{
  "openapi": "3.1.0",
  "info": {
    "title": "Sessionboard Public API",
    "version": "1.0",
    "description": "REST API for managing sessions, speakers, contacts, sponsors, exhibitors, and event data on the Sessionboard platform.",
    "contact": {
      "name": "Sessionboard Support",
      "email": "support@sessionboard.com"
    },
    "termsOfService": "https://www.sessionboard.com/legal/terms-of-service"
  },
  "servers": [
    {
      "url": "https://public-api.sessionboard.com",
      "description": "US Region"
    },
    {
      "url": "https://public-api-eu.sessionboard.com",
      "description": "EU Region"
    }
  ],
  "security": [
    {
      "ApiKey": []
    },
    {
      "BearerToken": []
    }
  ],
  "tags": [
    {
      "name": "Events",
      "description": "Manage events on the platform."
    },
    {
      "name": "Sessions",
      "description": "Search and retrieve sessions within an event."
    },
    {
      "name": "Session Writes",
      "description": "Create, update, delete, and restore sessions. Requires the `write:sessions` scope."
    },
    {
      "name": "Contact Writes",
      "description": "Create, update, delete, and restore contacts. Requires the `write:contacts` scope."
    },
    {
      "name": "Exhibitor Writes",
      "description": "Create, update, delete, and restore exhibitors. Requires the `write:exhibitors` scope."
    },
    {
      "name": "Sponsor Writes",
      "description": "Create, update, delete, and restore sponsors. Requires the `write:sponsors` scope."
    },
    {
      "name": "Field Writes",
      "description": "Create, update, and delete custom fields. Requires the `write:fields` scope."
    },
    {
      "name": "Speakers",
      "description": "Search and retrieve speakers within an event."
    },
    {
      "name": "Participants",
      "description": "Search and retrieve every contact holding a session role on an event —\nspeakers, chairpersons, moderators and custom roles — with the roles\neach one holds, and list the event's participant roles.\n"
    },
    {
      "name": "Contacts",
      "description": "Search and retrieve contacts at the organization or event level."
    },
    {
      "name": "Sponsors",
      "description": "Search and retrieve sponsors within an event."
    },
    {
      "name": "Exhibitors",
      "description": "Search and retrieve exhibitors within an event."
    },
    {
      "name": "Event Settings",
      "description": "Retrieve event configuration such as fields, tags, tracks, rooms, formats, levels, languages, and session statuses."
    },
    {
      "name": "GDPR",
      "description": "Manage GDPR data access and erasure requests."
    },
    {
      "name": "Insights",
      "description": "Query event data using SbQL, generate queries with AI, and manage dashboards."
    },
    {
      "name": "Metadata Writes",
      "description": "Create, update, and delete session metadata (rooms, tracks, tags, formats, levels, languages, statuses). Requires the `write:metadata` scope."
    },
    {
      "name": "Agenda Planning",
      "description": "Manage agenda drafts, draft sessions, scheduling rules, and evaluation personas. Requires the `write:events` scope."
    },
    {
      "name": "Dashboards & Widgets",
      "description": "Create, read, update, and delete dashboards and widgets at the event or organization level. Requires `write:events` scope for writes."
    },
    {
      "name": "Reports & Queries",
      "description": "Create, read, update, delete, and run saved SbQL queries/reports at the event or organization level. Requires `write:events` scope for writes."
    },
    {
      "name": "Transcriptions",
      "description": "Transcript text on sessions — fragments, summaries, insights, and translations. Requires `read:transcriptions` / `write:transcriptions` scopes."
    },
    {
      "name": "Session Recordings",
      "description": "Session audio files for recording archives (live capture or imported audio). Requires `read:transcriptions` / `write:transcriptions` scopes."
    },
    {
      "name": "Media",
      "description": "Upload video or audio files for automatic transcription. Requires `read:media` / `write:media` scopes."
    },
    {
      "name": "Session Files",
      "description": "Documents attached to sessions (PDFs, PowerPoint, Word, images, and similar).\nSimple upload: `POST .../files/upload` (multipart, max 50 MB).\nDirect-to-storage: create → PUT → complete (max 500 MB).\nRequires `read:sessions` / `write:sessions` scopes.\nSee the [Uploading session files](/guides/uploading-session-files) guide.\n"
    },
    {
      "name": "OAuth",
      "description": "OAuth 2.1 endpoints for AI client authorization (Claude, ChatGPT). Mounted at `/oauth/` (not `/v1/`)."
    },
    {
      "name": "Log Export",
      "description": "Pull your organization's API request, security and audit logs into a SIEM\nsuch as Splunk, Microsoft Sentinel or Elastic. Requires a dedicated API token\nwith the `read:audit_logs` scope, which can call nothing else.\nSee the [Exporting logs to a SIEM](/guides/exporting-logs-to-a-siem) guide.\n"
    },
    {
      "name": "Awards",
      "description": "Read and manage Awards programs and their categories, rounds, promo codes, submissions and reviews. Organization-level: paths start at `/v1/organization/{orgId}/awards`. Requires `read:awards` / `write:awards` scopes."
    }
  ],
  "paths": {
    "/v1/events": {
      "get": {
        "operationId": "list-events",
        "summary": "List events",
        "description": "Returns events accessible to the authenticated API key.\n\nResults are paginated: `page` (1–999, default 1) and `pageSize`\n(1–100, default 25) are honored, and the response wraps events in\nthe standard `{ results, pagination }` envelope. Events are ordered\noldest-first (`created_at` ascending, ties broken by `id`), so pages\nare stable across requests.\n\nBy default each event is `id`, `name`, `timezone`, `starts_at`,\n`ends_at`, and `features`. Pass `expand` to attach extra collections.\n\n`expand=custom_fields` includes org-defined event custom field values\n(`CustomFieldValue[]`). An event with no values returns `[]`.\nDatetime custom field values are ISO 8601 in the event's local time\nwith its UTC offset (for example `2026-08-15T09:00:00-03:00`); when\nthe event has no valid timezone the raw UTC instant is returned\n(`2026-08-15T12:00:00.000Z`). Date-only fields are unchanged.\n\n`expand=integration_mappings` includes conference connector mappings\n(`EventIntegrationMapping[]`) from `Integration_Event_Mapping_Union`\n(Cvent, Grip, Swoogo, Swapcard, ASP, Stova, Bizzabo, Gleanin,\nExpoPlatform, ON24). `source` is the union key (underscores, e.g.\n`expo_platform`). LiveBuzz / apps-engine campaign IDs are **not**\nincluded in this expand.\n\nRepeat the query param or comma-separate values:\n`?expand=custom_fields&expand=integration_mappings`\n",
        "tags": [
          "Events"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          },
          {
            "$ref": "#/components/parameters/ListEventsExpand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Event"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                },
                "example": {
                  "results": [
                    {
                      "id": 3960,
                      "name": "Acme Conference",
                      "timezone": "America/Chicago",
                      "starts_at": "2026-10-05T13:00:00.000Z",
                      "ends_at": "2026-10-07T22:00:00.000Z",
                      "features": {
                        "primary_speakers": true,
                        "speaker_acceptance": false,
                        "translated_fields": false
                      }
                    }
                  ],
                  "pagination": {
                    "currentPage": 1,
                    "pageSize": 25,
                    "totalPages": 4,
                    "totalResults": 97
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions": {
      "post": {
        "operationId": "search-sessions",
        "summary": "Search sessions",
        "description": "Search and filter sessions within an event. Supports pagination,\nsorting, filtering by status, date ranges, and session categorization\n(`trackIds`, `tagIds`, `levelIds`, `formatIds`, `languageIds`), and\nexpanding related data.\n\nEach categorization filter needs at least one ID. An empty array is\nrejected with a 400 naming the field — to apply no filter at all, omit\nthe property rather than sending `[]`.\n\n`sort` uses nested keys — each sortable field is an object with a\n`sort` direction, for example `{\"sort\": {\"startsAt\": {\"sort\": \"asc\"}}}`.\nThere is no flat `{\"order\": \"...\", \"sort\": \"...\"}` form. Sessions with\na null `starts_at` always sort last when sorting by `startsAt`,\nregardless of direction.\n\nEvery session includes `is_abstract` and `composition_status`. Pass\n`filters.isAbstract` to return only abstract submissions or only\nprogram sessions. By default, sessions linked as composition sources\nare excluded; pass `expand=linked_sources` to include them. Pass\n`expand=composition` for full target/source details.\n\nEach session in the response includes a `subsessions` array. By\ndefault each subsession is returned in a minimal shape (`Subsession`).\nPass `expand=subsession_details` in the request body to receive full\nparent-shape parity (`SubsessionDetailed`) on every subsession —\nincluding `status`, `custom_status`, `custom_fields`, `chairpersons`,\n`moderators`, `sponsors`, `exhibitors`, `tags`, `language`, `track`,\n`level`, `room`, etc.\n\nEach subsession inherits the parent session's `is_abstract`,\n`composition_status`, and optional `composition` graph (when\n`expand=composition` is set).\n\nNested `language`, `track`, `level`, `format`, and `room` objects on\neach session include the field sets documented on the `Session` schema.\nUnassigned metadata is returned as `{}`.\n\nPaginated search responses return matching sessions under `results`\n(not `data`), alongside a `pagination` object.\n",
        "tags": [
          "Sessions"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/SessionSearchBody"
              },
              "examples": {
                "sortByStartTime": {
                  "summary": "Sort by session start time (nested sort syntax)",
                  "description": "Sort keys are nested objects — `{\"startsAt\": {\"sort\": \"asc\"}}`.\nSessions with a null `starts_at` always sort last, regardless\nof direction.\n",
                  "value": {
                    "filters": {
                      "status": "accepted"
                    },
                    "sort": {
                      "startsAt": {
                        "sort": "asc"
                      }
                    }
                  }
                },
                "filterByCategorization": {
                  "summary": "Filter by tracks and tags",
                  "description": "IDs within one filter match with OR; separate filters combine\nwith AND.\n",
                  "value": {
                    "filters": {
                      "trackIds": [
                        "3fa85f64-5717-4562-b3fc-2c963f66afa6"
                      ],
                      "tagIds": [
                        "9b2f0c1d-8e47-4a6b-9c3d-1a2b3c4d5e6f"
                      ]
                    },
                    "sort": {
                      "startsAt": {
                        "sort": "asc"
                      }
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Session"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "get": {
        "operationId": "list-sessions",
        "summary": "List sessions (CRUD proxy)",
        "description": "Paginated list of top-level sessions via the CRUD proxy. Returns nested\n`language`, `track`, `level`, `format`, and `room` metadata using the same\nfield sets documented on the `Session` schema (`null` when unassigned).\nAlso includes `is_abstract` and `composition_status`.\n\nQuery params: `is_abstract` (`true`/`false`), `expand=linked_sources`,\n`expand=composition`, plus standard pagination and filters.\n\nSession categorization filters use snake_case query params on this\nendpoint: `track_id`/`track_ids`, `tag_id`/`tag_ids`,\n`level_id`/`level_ids`, `format_id`/`format_ids`,\n`language_id`/`language_ids`. Plural params take comma-separated UUIDs\n(OR within a filter; separate filters combine with AND).\n\nEvery value passed to these filters must be a UUID. A non-UUID value\nreturns `400` with error code `VALIDATION_ERROR` and a message naming\nthe offending parameter, for example\n`track_id must be a UUID (received \"nope\")`.\n",
        "tags": [
          "Sessions"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "name": "page_size",
            "in": "query",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "is_abstract",
            "in": "query",
            "schema": {
              "type": "boolean"
            },
            "description": "Filter to abstract submissions or program sessions."
          },
          {
            "$ref": "#/components/parameters/Expand"
          },
          {
            "name": "status",
            "in": "query",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "track_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "Filter by a single track UUID."
          },
          {
            "name": "track_ids",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Comma-separated track UUIDs (OR). Repeat `track_id` for the same effect."
          },
          {
            "name": "level_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "level_ids",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Comma-separated level UUIDs (OR)."
          },
          {
            "name": "format_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "format_ids",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Comma-separated format UUIDs (OR)."
          },
          {
            "name": "language_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "language_ids",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Comma-separated language UUIDs (OR)."
          },
          {
            "name": "tag_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "tag_ids",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Comma-separated tag UUIDs (OR)."
          },
          {
            "name": "search",
            "in": "query",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Session"
                      }
                    },
                    "pagination": {
                      "type": "object",
                      "properties": {
                        "current_page": {
                          "type": "integer"
                        },
                        "page_size": {
                          "type": "integer"
                        },
                        "total_pages": {
                          "type": "integer"
                        },
                        "total_results": {
                          "type": "integer"
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "A categorization filter param (`track_id`/`track_ids`,\n`level_id`/`level_ids`, `format_id`/`format_ids`,\n`language_id`/`language_ids`, `tag_id`/`tag_ids`) carried a\nnon-UUID value. The message names the offending parameter.\n",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "error": {
                      "type": "string",
                      "examples": [
                        "VALIDATION_ERROR"
                      ]
                    },
                    "message": {
                      "type": "string",
                      "examples": [
                        "track_id must be a UUID (received \"nope\")"
                      ]
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/status": {
      "post": {
        "operationId": "search-sessions-by-status",
        "summary": "Search sessions by status",
        "description": "Returns a lightweight list of session statuses, including deleted\nsessions. Supports filtering by `deletedAt` in addition to standard\nfilters.\n\nAlso accepts the five session categorization filters (`trackIds`,\n`tagIds`, `levelIds`, `formatIds`, `languageIds`). IDs within one\nfilter match with OR; separate filters combine with AND. The filters\nare evaluated against the **top-level (root) session**: a subsession\nrow matches when its parent carries the filtered attribute, so a\nmatching parent and the flat rows of its `subsessions` array stay\nconsistent. Unlike other session searches, a **deleted** root session\nstill satisfies a categorization filter — surfacing deleted sessions\nis this endpoint's purpose, and filtering must not hide them.\n\nEach categorization filter needs at least one ID. An empty array is\nrejected with a 400 naming the field — to apply no filter at all, omit\nthe property rather than sending `[]`.\n\nParent rows additionally include a `subsessions` array with the same\nminimal status-focused shape for each child subsession\n(`SubsessionStatus`). Subsession rows that appear in the flat\nresults continue to surface with their own row (for back-compat) and\ncarry an empty `subsessions` array.\n",
        "tags": [
          "Sessions"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "filters": {
                    "type": "object",
                    "properties": {
                      "createdAt": {
                        "$ref": "#/components/schemas/DateRangeFilter"
                      },
                      "updatedAt": {
                        "$ref": "#/components/schemas/DateRangeFilter"
                      },
                      "deletedAt": {
                        "$ref": "#/components/schemas/DateRangeFilter"
                      },
                      "status": {
                        "type": "string",
                        "enum": [
                          "accepted",
                          "accept_queue",
                          "pending",
                          "decline_queue",
                          "declined"
                        ]
                      },
                      "trackIds": {
                        "type": "array",
                        "minItems": 1,
                        "items": {
                          "type": "string",
                          "format": "uuid"
                        },
                        "description": "Match sessions in any of these tracks (OR). Combined with other filters using AND. Evaluated against the top-level session; a deleted root still matches. Send at least one ID — an empty array is rejected with a 400; to apply no track filter, omit the property."
                      },
                      "levelIds": {
                        "type": "array",
                        "minItems": 1,
                        "items": {
                          "type": "string",
                          "format": "uuid"
                        }
                      },
                      "formatIds": {
                        "type": "array",
                        "minItems": 1,
                        "items": {
                          "type": "string",
                          "format": "uuid"
                        }
                      },
                      "languageIds": {
                        "type": "array",
                        "minItems": 1,
                        "items": {
                          "type": "string",
                          "format": "uuid"
                        }
                      },
                      "tagIds": {
                        "type": "array",
                        "minItems": 1,
                        "items": {
                          "type": "string",
                          "format": "uuid"
                        },
                        "description": "Match sessions tagged with any of these tag IDs (OR). Send at least one ID — an empty array is rejected with a 400."
                      }
                    }
                  },
                  "sort": {
                    "type": "object",
                    "description": "Nested sort keys — the same shape as other search endpoints\n(`{\"createdAt\": {\"sort\": \"desc\"}}`), not a flat\n`{\"order\": \"createdAt\", \"sort\": \"desc\"}` pair.\n\nWhen sorting by `deletedAt`, deleted sessions sort before\nnever-deleted ones (whose `deleted_at` is null) in both\ndirections.\n",
                    "properties": {
                      "createdAt": {
                        "$ref": "#/components/schemas/NestedSortField"
                      },
                      "updatedAt": {
                        "$ref": "#/components/schemas/NestedSortField"
                      },
                      "deletedAt": {
                        "$ref": "#/components/schemas/NestedSortField"
                      }
                    }
                  },
                  "expand": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  }
                }
              },
              "examples": {
                "recentlyDeletedFirst": {
                  "summary": "Sort by deletion time (nested sort syntax)",
                  "value": {
                    "filters": {
                      "status": "declined"
                    },
                    "sort": {
                      "deletedAt": {
                        "sort": "desc"
                      }
                    }
                  }
                },
                "declinedInTrack": {
                  "summary": "Declined sessions in a track (categorization filter)",
                  "description": "IDs within one filter match with OR; separate filters combine\nwith AND. Filters match the top-level session, so subsession\nrows match via their parent — and a deleted root session\nstill matches.\n",
                  "value": {
                    "filters": {
                      "status": "declined",
                      "trackIds": [
                        "3fa85f64-5717-4562-b3fc-2c963f66afa6"
                      ]
                    },
                    "sort": {
                      "deletedAt": {
                        "sort": "desc"
                      }
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/SessionStatus"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}": {
      "get": {
        "operationId": "get-session",
        "summary": "Get a session",
        "description": "Retrieve a single session by ID, optionally expanding related data.\n\nEvery session includes `is_abstract` and `composition_status`. Pass\n`expand=composition` for full linked target and source details.\n\nAccepts both parent session UUIDs and subsession UUIDs. When called\nwith a subsession UUID, the response is a full session-shaped DTO\nfor that subsession (with `parent_session_friendly_id` /\n`parent_session_friendly_id_raw` keys and no nested `subsessions`\narray). Subsessions inherit the parent session's `is_abstract`,\n`composition_status`, and optional `composition` graph (when\n`expand=composition` is set) — subsessions cannot participate in\ncomposition directly.\n\nThis means callers can iterate `parent.subsessions[]` and then call\nthis endpoint with each subsession id to retrieve the same shape\nas a parent session.\n\nPass `expand=subsession_details` to receive the full\n`SubsessionDetailed` shape on every entry of `parent.subsessions[]`;\nthe flag has no effect at the top level — the top-level response\nalways returns the full shape regardless of whether the requested\nid is a parent or a subsession.\n",
        "tags": [
          "Sessions"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sessionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The session ID."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Session"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Session not found"
          }
        }
      },
      "put": {
        "operationId": "update-session",
        "summary": "Update a session",
        "description": "Update an existing session. Requires the `write:sessions` scope. Send `updated_at` from the last-fetched session for optimistic concurrency control.",
        "tags": [
          "Session Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sessionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The session ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "updated_at": {
                    "type": "string",
                    "format": "date-time",
                    "description": "Required for optimistic concurrency control. Send the `updated_at` value from the last-fetched session."
                  },
                  "title": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  },
                  "starts_at": {
                    "type": "string",
                    "format": "date-time"
                  },
                  "ends_at": {
                    "type": "string",
                    "format": "date-time"
                  },
                  "capacity": {
                    "type": "integer"
                  },
                  "room_id": {
                    "type": "string",
                    "format": "uuid"
                  },
                  "track_id": {
                    "type": "string",
                    "format": "uuid"
                  },
                  "status": {
                    "type": "string"
                  },
                  "tag_ids": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "format": "uuid"
                    }
                  },
                  "is_public": {
                    "type": "boolean"
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Session updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Session"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "Session not found"
          },
          "409": {
            "description": "Stale update — session modified since last fetch"
          }
        }
      },
      "delete": {
        "operationId": "delete-session",
        "summary": "Soft-delete a session",
        "description": "Soft-delete a session. Can be restored with the restore endpoint. Requires the `write:sessions` scope.",
        "tags": [
          "Session Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sessionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The session ID."
          }
        ],
        "responses": {
          "200": {
            "description": "Session deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "Session not found"
          },
          "409": {
            "description": "Cannot delete — has active subsessions"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/fields": {
      "put": {
        "operationId": "update-session-fields",
        "summary": "Update session custom fields",
        "description": "Update custom field values on a session without touching other session properties. Requires the `write:sessions` scope.",
        "tags": [
          "Session Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sessionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The session ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "values"
                ],
                "properties": {
                  "values": {
                    "type": "array",
                    "minItems": 1,
                    "description": "Field values to write. Unlike the session `PUT`, this\nendpoint takes an array of entries rather than a\n`custom_fields` object, and each entry may carry its own\n`language` — so this is the endpoint to use for writing a\nlanguage variant of a single field. An empty or missing\narray returns `400` `VALIDATION_ERROR`.\n\nValue formatting per type matches `custom_fields`\nelsewhere: an empty string (`\"\"`) clears a `number`,\n`currency`, or `percent` field; `checkbox` takes boolean\n`true` / `false`; `datetime` takes an ISO 8601 string.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`.\n",
                    "items": {
                      "type": "object",
                      "required": [
                        "internal_name"
                      ],
                      "properties": {
                        "internal_name": {
                          "type": "string",
                          "description": "The field's internal name, as listed by `GET /v1/event/{eventId}/fields`."
                        },
                        "value": {
                          "description": "The value to store. `null` clears it.",
                          "nullable": true
                        },
                        "language": {
                          "type": "string",
                          "description": "Optional locale for a language variant (for example `es_ES`). Must be one of the event's enabled locales. Omit it to write the event default.\n"
                        }
                      }
                    }
                  }
                }
              },
              "examples": {
                "single": {
                  "summary": "Write one field value",
                  "value": {
                    "values": [
                      {
                        "internal_name": "track_code",
                        "value": "T-42"
                      }
                    ]
                  }
                },
                "variant": {
                  "summary": "Write a Spanish variant of one field",
                  "value": {
                    "values": [
                      {
                        "internal_name": "session_subtitle",
                        "value": "Sesión de apertura",
                        "language": "es_ES"
                      }
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Custom fields updated. The response echoes the fields that were\nwritten rather than the whole session — refetch with\n`GET /v1/event/{eventId}/sessions/{sessionId}` if you need the\nfull record.\n",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "object",
                      "properties": {
                        "session_id": {
                          "type": "string",
                          "format": "uuid"
                        },
                        "updated_fields": {
                          "type": "array",
                          "items": {
                            "type": "object",
                            "properties": {
                              "field_id": {
                                "type": "string",
                                "format": "uuid"
                              },
                              "language": {
                                "type": "string",
                                "description": "Present only when the request specified a language."
                              }
                            }
                          }
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Validation error — `values` missing or empty, an unknown field (`UNKNOWN_FIELD`), a type mismatch (`TYPE_MISMATCH`), or an integration-owned field (`FIELD_READ_ONLY`).\n"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "Session not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/speakers": {
      "post": {
        "operationId": "search-speakers",
        "summary": "Search speakers",
        "description": "Search and filter speakers within an event. Supports the session\ncategorization filters (`trackIds`, `tagIds`, `levelIds`, `formatIds`,\n`languageIds`) to match speakers by the sessions they are assigned to.\n`sort` uses the same nested shape as other search endpoints\n(`{\"createdAt\": {\"sort\": \"desc\"}}`).\n\nCategorization filters are evaluated against the **top-level\nsession**, matching session search semantics: a speaker assigned to a\nsubsession matches when the subsession's parent (root) session\nsatisfies the filter — a subsession's own categorization values are\nnot consulted.\n\nEach categorization filter needs at least one ID. An empty array is\nrejected with a 400 naming the field — to apply no filter at all, omit\nthe property rather than sending `[]`.\n\nOnly a session's **speakers** are matched. A contact attached to a\nmatching session as a chairperson, moderator or other participant is\nnot returned by this endpoint — with or without a filter. The session\nobject from `POST /v1/event/{eventId}/sessions` exposes four separate\nparticipant arrays (`speakers`, `chairpersons`, `moderators`,\n`participants`) and they are not interchangeable here: reconciling\n\"speakers on track X\" against a session search must compare against\nthe `speakers` array alone, or the counts will not agree. The same\ncontact can appear under different roles on different sessions, so a\ncontact present in the unfiltered speaker list may still be absent\nfrom a filtered one when its attachment to the matching session is a\nnon-speaker role.\n\nTo retrieve every participant regardless of role — chairpersons,\nmoderators and custom roles included, each with the roles it holds —\nuse `POST /v1/event/{eventId}/participants`. It accepts the same\nfilters and returns the same contact fields plus a `roles` array.\n",
        "tags": [
          "Speakers"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/SpeakerSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Contact"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/speakers/{contactId}": {
      "get": {
        "operationId": "get-speaker",
        "summary": "Get a speaker",
        "description": "Retrieve a single speaker by contact ID.",
        "tags": [
          "Speakers"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The contact ID."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Contact"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Speaker not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/participants": {
      "post": {
        "operationId": "search-participants",
        "summary": "Search participants",
        "description": "Search every contact assigned to at least one session on the event in\n**any** participant role — the standard roles (speaker, chairperson,\nmoderator) and any custom role configured for the event (Panelist,\nCoach, Author, …). This is the superset of\n`POST /v1/event/{eventId}/speakers`, which matches speakers only.\n\nEach contact is returned **once**, however many sessions or roles it\nholds, with a `roles` array listing every role it has on the event and\nthe session ids where it holds each one. Every other field is the same\n`Contact` shape `POST /speakers` returns, in the same order, with\n`roles` appended last. `roles` always describes the contact's full\nset of roles on the event — it is not narrowed by the request filters,\nso a search filtered to the Moderator role still shows that a result is\nalso a Speaker elsewhere on the program.\n\n**Filters.** Every Search Speakers filter is accepted and behaves the\nsame: `createdAt`, `updatedAt`, `status` (the *session's* status),\n`trackIds`, `levelIds`, `formatIds`, `languageIds`, `tagIds`, plus\n`sort` and `expand`. Categorization filters are evaluated against the\n**top-level session**, so a participant on a subsession matches when\nthe subsession's parent satisfies the filter. Each array filter needs\nat least one id — `[]` is a `400` naming the field; omit the property\nto apply no filter.\n\nThree filters are specific to this endpoint:\n\n- `roleIds` — return only participants holding **at least one** of the\n  given roles, standard or custom. Get the ids from\n  `GET /v1/event/{eventId}/participant-roles`.\n- `roleSlugs` — the same, by role slug (`speaker`, `chairperson`,\n  `moderator`, or a custom role's slug). Use this to get every speaker\n  without resolving ids per event, or on older events where roles have\n  `roleId: null`.\n- `email` — exact, case-insensitive match on the contact's email. An\n  unknown address returns an empty `results` array with\n  `totalResults: 0`, not an error. For a single-record lookup that\n  answers `404` instead, use `GET /v1/event/{eventId}/participants?email=`.\n\n**Roles on older events.** Roles are stored per event. An event that\nhas never been opened in the Sessions editor may not have its standard\nroles created yet; its participants are still returned, but a\nstandard role on such an event has `roleId: null` (with `roleName`,\n`slug` and `coreRole` filled in) and cannot be matched by `roleIds`\nuntil the roles exist — filter by `roleSlugs` instead.\n`GET .../participant-roles` returns an empty list for such an event.\n",
        "tags": [
          "Participants"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ParticipantSearchBody"
              },
              "examples": {
                "byRole": {
                  "summary": "Everyone holding the Moderator or a custom role",
                  "value": {
                    "filters": {
                      "roleIds": [
                        "4efeb845-050f-4002-9496-cb586cdf10f2",
                        "52d60237-19db-4bda-a116-8b9fcb6750e9"
                      ],
                      "status": "accepted"
                    }
                  }
                },
                "bySlug": {
                  "summary": "Every speaker, by role slug",
                  "value": {
                    "filters": {
                      "roleSlugs": [
                        "speaker"
                      ]
                    }
                  }
                },
                "byEmail": {
                  "summary": "Match one contact by email",
                  "value": {
                    "filters": {
                      "email": "jane.smith@university.edu"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Participant"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Validation error — an empty filter array, a non-UUID in `roleIds`, or an out-of-range `page` / `pageSize`."
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "get": {
        "operationId": "get-participant-by-email",
        "summary": "Get a participant by email",
        "description": "Look up one participant by email address. The match is exact and\ncase-insensitive. Returns the participant, or `404` when no contact\nwith that address holds a session role on the event.\n\nSearch on this API is a `POST`, so a `GET` on the collection path is\nfree for the lookup — no `/by-email` sub-path is needed. `email` is\nrequired; a bare `GET /participants` is a `400`, not an unpaginated\nlist.\n\nContacts are not unique by email. If more than one contact on the\nevent shares the address, the earliest-created one is returned; use\n`POST /v1/event/{eventId}/participants` with the `email` filter to see\nthem all.\n",
        "tags": [
          "Participants"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "email",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "format": "email"
            },
            "description": "The contact's email address. Matched exactly, ignoring case."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Participant"
                }
              }
            }
          },
          "400": {
            "description": "`email` is missing or empty."
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found, or no participant with that email on the event."
          }
        }
      }
    },
    "/v1/event/{eventId}/participants/{contactId}": {
      "get": {
        "operationId": "get-participant",
        "summary": "Get a participant",
        "description": "Retrieve a single participant by contact ID, with the `roles` it holds\non the event. `404` when the contact is not on the event, or is on the\nevent but holds no session role — a contact returned by\n`GET /v1/event/{eventId}/contacts/{contactId}` is not necessarily a\nparticipant.\n",
        "tags": [
          "Participants"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The contact ID."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Participant"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Participant not found on this event"
          }
        }
      }
    },
    "/v1/event/{eventId}/participant-roles": {
      "get": {
        "operationId": "list-participant-roles",
        "summary": "List participant roles",
        "description": "The event's participant roles — the three standard roles (Speaker,\nChairperson, Moderator) and every custom role configured for the\nevent — with the ids to use in the `roleIds` filter of\n`POST /v1/event/{eventId}/participants`. Ordered as the Sessions\nsettings page shows them. Deleted roles are not returned.\n\n`is_custom` is `true` for roles the organizer added. `core_role` is\nthe standard category a custom role maps to (`speaker`,\n`chairperson` or `moderator`); it decides which legacy array the\nrole's participants appear in on `POST /v1/event/{eventId}/sessions`,\nand is not a display label — use `name`.\n\nAn event that has never been opened in the Sessions editor may have no\nroles yet and answers with an empty `results` array. Its participants\nare still returned by `POST .../participants`, with `roleId: null` on\ntheir standard roles until the roles are created.\n",
        "tags": [
          "Participants"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/EventParticipantRole"
                      }
                    }
                  }
                },
                "examples": {
                  "withCustomRoles": {
                    "value": {
                      "results": [
                        {
                          "id": "84bd12e5-d5ec-4c64-a604-4051e06c8dc2",
                          "name": "Speaker",
                          "name_plural": "Speakers",
                          "slug": "speaker",
                          "core_role": "speaker",
                          "is_custom": false,
                          "sort_order": 0,
                          "created_at": "2026-02-03T18:04:11.120Z",
                          "updated_at": "2026-02-03T18:04:11.120Z"
                        },
                        {
                          "id": "4efeb845-050f-4002-9496-cb586cdf10f2",
                          "name": "Moderator",
                          "name_plural": "Moderators",
                          "slug": "moderator",
                          "core_role": "moderator",
                          "is_custom": false,
                          "sort_order": 2,
                          "created_at": "2026-02-03T18:04:11.120Z",
                          "updated_at": "2026-02-03T18:04:11.120Z"
                        },
                        {
                          "id": "52d60237-19db-4bda-a116-8b9fcb6750e9",
                          "name": "Panelist",
                          "name_plural": "Panelists",
                          "slug": "panelist",
                          "core_role": "speaker",
                          "is_custom": true,
                          "sort_order": 3,
                          "created_at": "2026-02-10T09:41:52.004Z",
                          "updated_at": "2026-02-10T09:41:52.004Z"
                        }
                      ]
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/organization/{orgId}/contacts": {
      "post": {
        "operationId": "search-org-contacts",
        "summary": "Search organization contacts",
        "description": "Search and filter contacts across the organization.",
        "tags": [
          "Contacts"
        ],
        "parameters": [
          {
            "name": "orgId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The organization ID (UUID)."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Contact"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Organization not found"
          }
        }
      }
    },
    "/v1/organization/{orgId}/contacts/{contactId}": {
      "get": {
        "operationId": "get-org-contact",
        "summary": "Get an organization contact",
        "description": "Retrieve a single contact by ID at the organization level.",
        "tags": [
          "Contacts"
        ],
        "parameters": [
          {
            "name": "orgId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The organization ID (UUID)."
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The contact ID."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Contact"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Contact not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/contacts": {
      "post": {
        "operationId": "search-event-contacts",
        "summary": "Search event contacts",
        "description": "Search and filter contacts within an event.",
        "tags": [
          "Contacts"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Contact"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/contacts/{contactId}": {
      "get": {
        "operationId": "get-event-contact",
        "summary": "Get an event contact",
        "description": "Retrieve a single contact by ID at the event level.",
        "tags": [
          "Contacts"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The contact ID."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Contact"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Contact not found"
          }
        }
      },
      "put": {
        "operationId": "update-contact",
        "summary": "Update a contact",
        "description": "Update an existing contact. Requires the `write:contacts` scope. Optionally send `updated_at` for optimistic concurrency control. Sending `null` for a standard field clears it; omitting a key leaves it unchanged.",
        "tags": [
          "Contact Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The contact ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "updated_at": {
                    "type": "string",
                    "format": "date-time",
                    "description": "Optional optimistic concurrency control. Send the `updated_at` value from the last-fetched contact."
                  },
                  "first_name": {
                    "type": "string"
                  },
                  "last_name": {
                    "type": "string"
                  },
                  "email": {
                    "type": "string",
                    "format": "email"
                  },
                  "company": {
                    "type": "string"
                  },
                  "title": {
                    "type": "string"
                  },
                  "phone": {
                    "type": "string"
                  },
                  "about": {
                    "type": "string",
                    "description": "Biography. HTML is allowed and stored as rich text."
                  },
                  "salutation": {
                    "type": "string"
                  },
                  "honorific": {
                    "type": "string"
                  },
                  "address_line_1": {
                    "type": "string"
                  },
                  "address_line_2": {
                    "type": "string"
                  },
                  "address_city": {
                    "type": "string"
                  },
                  "address_state": {
                    "type": "string"
                  },
                  "address_postal_code": {
                    "type": "string"
                  },
                  "address_country": {
                    "type": "string",
                    "description": "ISO 3166-1 numeric code (as GET returns), alpha-2 or alpha-3 code, or English country name. Stored and returned as the numeric code. An unknown value returns `400` naming the field and nothing is written."
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Contact updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Contact"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:contacts scope"
          },
          "404": {
            "description": "Contact not found"
          },
          "409": {
            "description": "Stale update — contact modified since last fetch"
          }
        }
      },
      "delete": {
        "operationId": "delete-contact",
        "summary": "Soft-delete a contact",
        "description": "Soft-delete a contact. Can be restored with the restore endpoint. Requires the `write:contacts` scope.",
        "tags": [
          "Contact Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The contact ID."
          }
        ],
        "responses": {
          "200": {
            "description": "Contact deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:contacts scope"
          },
          "404": {
            "description": "Contact not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sponsors": {
      "post": {
        "operationId": "search-sponsors",
        "summary": "Search sponsors",
        "description": "Search and filter sponsors within an event. Returns the account records carrying the Sponsor role on this event — an account holding both roles is returned by both searches, and contacts are never returned.\n",
        "tags": [
          "Sponsors"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Sponsor"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sponsors/{sponsorId}": {
      "get": {
        "operationId": "get-sponsor",
        "summary": "Get a sponsor",
        "description": "Retrieve a single sponsor by ID.",
        "tags": [
          "Sponsors"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sponsorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The sponsor ID."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Sponsor"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "No sponsor with this id on this event. A record that exists but does not hold the sponsor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds.\n"
          }
        }
      },
      "put": {
        "operationId": "update-sponsor",
        "summary": "Update a sponsor",
        "description": "Update an existing sponsor. Requires the `write:sponsors` scope. Optionally send `updated_at` for optimistic concurrency control.",
        "tags": [
          "Sponsor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sponsorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The sponsor ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "updated_at": {
                    "type": "string",
                    "format": "date-time",
                    "description": "Optional optimistic concurrency control. Send the `updated_at` value from the last-fetched sponsor."
                  },
                  "name": {
                    "type": "string",
                    "description": "New sponsor name. Must be a non-empty string when present — an explicit empty string returns `400`. Omit the key to leave the name unchanged.\n"
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Sponsor updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Sponsor"
                },
                "example": {
                  "id": "7f5e2c1a-9b3d-4e6f-8a2b-1c4d5e6f7a8b",
                  "friendly_id": "SPO-12",
                  "name": "Globex Corporation",
                  "custom_fields": []
                }
              }
            }
          },
          "400": {
            "description": "Validation error — `name`, when present, must be a non-empty string"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sponsors scope"
          },
          "404": {
            "description": "No sponsor with this id on this event. A record that exists but does not hold the sponsor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds.\n"
          },
          "409": {
            "description": "Stale update — sponsor modified since last fetch"
          }
        }
      },
      "delete": {
        "operationId": "delete-sponsor",
        "summary": "Soft-delete a sponsor",
        "description": "Soft-delete a sponsor. Can be restored with the restore endpoint. Requires the `write:sponsors` scope.\n\n**This deletes the group, not just its sponsor role.** The path names the role you are calling under, but the record that gets soft-deleted is the underlying group, so:\n\n* A group holding **both** roles loses its exhibitor role too. After\n  this call it is absent from both searches and both `GET`s answer\n  `404`.\n\n* A group linked to **other events** is removed from those events as\n  well — it is no longer returned by any event's sponsor or exhibitor\n  search across the organization.\n\n\nThis matches the admin UI, where the unit of deletion is the group, not one of its roles. There is no role-scoped or event-scoped delete on this API. If you only want to stop listing a partner for one season, do not call this endpoint.\n\n`POST /v1/event/{eventId}/sponsors/{sponsorId}/restore` reverses it with the same reach — both roles and every event come back — so nothing is lost permanently.\n",
        "tags": [
          "Sponsor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sponsorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The sponsor ID."
          }
        ],
        "responses": {
          "204": {
            "description": "Sponsor deleted. The response has no body — do not expect a `200` or a JSON payload.\n"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sponsors scope"
          },
          "404": {
            "description": "No sponsor with this id on this event. A record that exists but does not hold the sponsor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds. An **already-deleted** sponsor is also a `404`, so a repeated delete is safe but is not reported as a success.\n"
          }
        }
      }
    },
    "/v1/event/{eventId}/exhibitors": {
      "post": {
        "operationId": "search-exhibitors",
        "summary": "Search exhibitors",
        "description": "Search and filter exhibitors within an event. Returns the account records carrying the Exhibitor role on this event — an account holding both roles is returned by both searches, and contacts are never returned.\n",
        "tags": [
          "Exhibitors"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Exhibitor"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/exhibitors/{exhibitorId}": {
      "get": {
        "operationId": "get-exhibitor",
        "summary": "Get an exhibitor",
        "description": "Retrieve a single exhibitor by ID.",
        "tags": [
          "Exhibitors"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "exhibitorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The exhibitor ID."
          },
          {
            "$ref": "#/components/parameters/Expand"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Exhibitor"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "No exhibitor with this id on this event. A record that exists but does not hold the exhibitor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds.\n"
          }
        }
      },
      "put": {
        "operationId": "update-exhibitor",
        "summary": "Update an exhibitor",
        "description": "Update an existing exhibitor. Requires the `write:exhibitors` scope. Optionally send `updated_at` for optimistic concurrency control.",
        "tags": [
          "Exhibitor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "exhibitorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The exhibitor ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "updated_at": {
                    "type": "string",
                    "format": "date-time",
                    "description": "Optional optimistic concurrency control. Send the `updated_at` value from the last-fetched exhibitor."
                  },
                  "name": {
                    "type": "string",
                    "description": "New exhibitor name. When present it must be a non-empty string — an explicit empty string returns `400`. Omit the key to leave the name unchanged."
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Exhibitor updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Exhibitor"
                },
                "example": {
                  "id": "4b1de9c7-88a2-4e0f-b1f3-6a9d0c2e4f22",
                  "friendly_id": "EXH-8",
                  "name": "Initech Booth Services",
                  "custom_fields": []
                }
              }
            }
          },
          "400": {
            "description": "Validation error — `name`, when present, must be a non-empty string"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:exhibitors scope"
          },
          "404": {
            "description": "No exhibitor with this id on this event. A record that exists but does not hold the exhibitor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds.\n"
          },
          "409": {
            "description": "Stale update — exhibitor modified since last fetch"
          }
        }
      },
      "delete": {
        "operationId": "delete-exhibitor",
        "summary": "Soft-delete an exhibitor",
        "description": "Soft-delete an exhibitor. Can be restored with the restore endpoint. Requires the `write:exhibitors` scope.\n\n**This deletes the group, not just its exhibitor role.** The path names the role you are calling under, but the record that gets soft-deleted is the underlying group, so:\n\n* A group holding **both** roles loses its sponsor role too. After\n  this call it is absent from both searches and both `GET`s answer\n  `404`.\n\n* A group linked to **other events** is removed from those events as\n  well — it is no longer returned by any event's sponsor or exhibitor\n  search across the organization.\n\n\nThis matches the admin UI, where the unit of deletion is the group, not one of its roles. There is no role-scoped or event-scoped delete on this API. If you only want to stop listing a partner for one season, do not call this endpoint.\n\n`POST /v1/event/{eventId}/exhibitors/{exhibitorId}/restore` reverses it with the same reach — both roles and every event come back — so nothing is lost permanently.\n",
        "tags": [
          "Exhibitor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "exhibitorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The exhibitor ID."
          }
        ],
        "responses": {
          "204": {
            "description": "Exhibitor deleted. The response has no body — do not expect a `200` or a JSON payload.\n"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:exhibitors scope"
          },
          "404": {
            "description": "No exhibitor with this id on this event. A record that exists but does not hold the exhibitor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds. An **already-deleted** exhibitor is also a `404`, so a repeated delete is safe but is not reported as a success.\n"
          }
        }
      }
    },
    "/v1/event/{eventId}/fields": {
      "get": {
        "operationId": "list-fields",
        "summary": "List fields",
        "description": "Returns all field definitions for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/Field"
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "post": {
        "operationId": "search-fields",
        "summary": "Search fields",
        "description": "Search and filter field definitions for an event, including standard and custom fields.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "filters": {
                    "type": "object",
                    "properties": {
                      "module": {
                        "type": "string",
                        "enum": [
                          "session",
                          "account",
                          "contact"
                        ],
                        "description": "Filter by module type."
                      },
                      "source": {
                        "type": "string",
                        "enum": [
                          "standard",
                          "custom"
                        ],
                        "description": "Filter by field source."
                      },
                      "scope": {
                        "type": "string",
                        "enum": [
                          "global",
                          "event"
                        ],
                        "description": "Filter by field scope."
                      },
                      "createdAt": {
                        "$ref": "#/components/schemas/DateRangeFilter"
                      },
                      "updatedAt": {
                        "$ref": "#/components/schemas/DateRangeFilter"
                      }
                    }
                  },
                  "sort": {
                    "$ref": "#/components/schemas/SortOptions"
                  },
                  "expand": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Field"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/tags": {
      "get": {
        "operationId": "list-tags",
        "summary": "List tags",
        "description": "Returns the event's taxonomy tags (the tags organizers create and apply\nto sessions in the app), paginated, newest first.\n",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Tag"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "post": {
        "operationId": "search-tags",
        "summary": "Search tags",
        "description": "Returns a paginated list of tags for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Tag"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/languages": {
      "get": {
        "operationId": "list-languages",
        "summary": "List languages",
        "description": "Returns the event's languages, newest first.\n\nPaginated: up to `pageSize` per page (default 25, maximum 100),\nwith a `pagination` object alongside the results. This page\npreviously described an unpaginated array, which is why a caller\nwith more than 25 languages appeared to be missing some.\n",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Language"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "post": {
        "operationId": "search-languages",
        "summary": "Search languages",
        "description": "Returns a paginated list of languages configured for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Language"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/formats": {
      "get": {
        "operationId": "list-formats",
        "summary": "List formats",
        "description": "Returns the event's session formats, newest first.\n\nPaginated: up to `pageSize` per page (default 25, maximum 100),\nwith a `pagination` object alongside the results. This page\npreviously described an unpaginated array, which is why a caller\nwith more than 25 session formats appeared to be missing some.\n",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Format"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "post": {
        "operationId": "search-formats",
        "summary": "Search formats",
        "description": "Returns a paginated list of session formats for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Format"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/tracks": {
      "get": {
        "operationId": "list-tracks",
        "summary": "List tracks",
        "description": "Returns the event's tracks, newest first.\n\nPaginated: up to `pageSize` per page (default 25, maximum 100),\nwith a `pagination` object alongside the results. This page\npreviously described an unpaginated array, which is why a caller\nwith more than 25 tracks appeared to be missing some.\n",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Track"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "post": {
        "operationId": "search-tracks",
        "summary": "Search tracks",
        "description": "Returns a paginated list of tracks for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Track"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/levels": {
      "get": {
        "operationId": "list-levels",
        "summary": "List levels",
        "description": "Returns the event's session levels, newest first.\n\nPaginated: up to `pageSize` per page (default 25, maximum 100),\nwith a `pagination` object alongside the results. This page\npreviously described an unpaginated array, which is why a caller\nwith more than 25 session levels appeared to be missing some.\n",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Level"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "post": {
        "operationId": "search-levels",
        "summary": "Search levels",
        "description": "Returns a paginated list of session levels for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Level"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/rooms": {
      "get": {
        "operationId": "list-rooms",
        "summary": "List rooms",
        "description": "Returns the event's rooms, newest first.\n\nPaginated: up to `pageSize` per page (default 25, maximum 100),\nwith a `pagination` object alongside the results. This page\npreviously described an unpaginated array, which is why a caller\nwith more than 25 rooms appeared to be missing some.\n",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Room"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      },
      "post": {
        "operationId": "search-rooms",
        "summary": "Search rooms",
        "description": "Returns a paginated list of rooms for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Room"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/statuses": {
      "get": {
        "operationId": "list-statuses",
        "summary": "List session statuses",
        "description": "Returns the event's session status definitions, newest first.\n\nPaginated: up to `pageSize` per page (default 25, maximum 100),\nwith a `pagination` object alongside the results. This page\npreviously described an unpaginated array, which is why a caller\nwith more than 25 session status definitions appeared to be missing some.\n",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/SessionCustomStatus"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/session-statuses": {
      "post": {
        "operationId": "search-session-statuses",
        "summary": "Search session statuses",
        "description": "Returns a paginated list of custom session status definitions for an event.",
        "tags": [
          "Event Settings"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RecordSearchBody"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/SessionCustomStatus"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/rooms/create": {
      "post": {
        "operationId": "create-room",
        "summary": "Create a room",
        "description": "Create a new room. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "capacity": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Room created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Room"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/rooms/{id}": {
      "put": {
        "operationId": "update-room",
        "summary": "Update a room",
        "description": "Update a room. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "capacity": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Room updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Room"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-room",
        "summary": "Delete a room",
        "description": "Delete a room. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Room deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/tracks/create": {
      "post": {
        "operationId": "create-track",
        "summary": "Create a track",
        "description": "Create a new track. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "color": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Track created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Track"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/tracks/{id}": {
      "put": {
        "operationId": "update-track",
        "summary": "Update a track",
        "description": "Update a track. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "color": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Track updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Track"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-track",
        "summary": "Delete a track",
        "description": "Delete a track. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Track deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/tags/create": {
      "post": {
        "operationId": "create-tag",
        "summary": "Create a tag",
        "description": "Create a new event taxonomy tag. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "color": {
                    "type": "string"
                  },
                  "order": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Tag created",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/Tag"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Missing required field (name)"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/tags/{id}": {
      "put": {
        "operationId": "update-tag",
        "summary": "Update a tag",
        "description": "Update a tag. Requires the `write:metadata` scope.\n\nSupports optimistic concurrency: pass the `updated_at` you last read\nand the request fails with `409` (`STALE_UPDATE`) if the tag changed\nsince then.\n",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "color": {
                    "type": "string"
                  },
                  "order": {
                    "type": "integer"
                  },
                  "updated_at": {
                    "type": "string",
                    "description": "Last-read `updated_at` for optimistic concurrency."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Tag updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/Tag"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          },
          "404": {
            "description": "Tag not found"
          },
          "409": {
            "description": "Stale update — tag modified since last fetch (STALE_UPDATE)"
          }
        }
      },
      "delete": {
        "operationId": "delete-tag",
        "summary": "Delete a tag",
        "description": "Delete a tag. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Tag deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          },
          "404": {
            "description": "Tag not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/formats/create": {
      "post": {
        "operationId": "create-format",
        "summary": "Create a format",
        "description": "Create a new session format. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Format created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Format"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/formats/{id}": {
      "put": {
        "operationId": "update-format",
        "summary": "Update a format",
        "description": "Update a session format. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Format updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Format"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-format",
        "summary": "Delete a format",
        "description": "Delete a session format. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Format deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/levels/create": {
      "post": {
        "operationId": "create-level",
        "summary": "Create a level",
        "description": "Create a new session level. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Level created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Level"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/levels/{id}": {
      "put": {
        "operationId": "update-level",
        "summary": "Update a level",
        "description": "Update a session level. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Level updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Level"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-level",
        "summary": "Delete a level",
        "description": "Delete a session level. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Level deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/languages/create": {
      "post": {
        "operationId": "create-language",
        "summary": "Create a language",
        "description": "Create a new language. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Language created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Language"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/languages/{id}": {
      "put": {
        "operationId": "update-language",
        "summary": "Update a language",
        "description": "Update a language. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Language updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Language"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-language",
        "summary": "Delete a language",
        "description": "Delete a language. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Language deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/statuses/create": {
      "post": {
        "operationId": "create-status",
        "summary": "Create a session status",
        "description": "Create a new custom session status. Requires the `write:metadata`\nscope.\n\nUnlike the other metadata endpoints, `name` alone is **not** enough.\n`color` and `status` are stored NOT NULL with no defaults, so all three\nare required; a payload missing either answers\n`400 VALIDATION_ERROR` naming the field.\n\n`status` is the underlying approval state this custom label maps onto —\nseveral labels may share one. It must be one of the five values below;\nanything else is a `400`, not a `500`.\n",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name",
                  "color",
                  "status"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "color": {
                    "type": "string"
                  },
                  "status": {
                    "type": "string",
                    "description": "Approval state this custom status maps onto.",
                    "enum": [
                      "pending",
                      "accepted",
                      "declined",
                      "accept_queue",
                      "decline_queue"
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Status created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionCustomStatus"
                }
              }
            }
          },
          "400": {
            "description": "Missing name, color or status, or a status outside the enum"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/statuses/{id}": {
      "put": {
        "operationId": "update-status",
        "summary": "Update a session status",
        "description": "Update a custom session status. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "color": {
                    "type": "string"
                  },
                  "status": {
                    "type": "string",
                    "description": "Approval state this custom status maps onto.",
                    "enum": [
                      "pending",
                      "accepted",
                      "declined",
                      "accept_queue",
                      "decline_queue"
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Status updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionCustomStatus"
                }
              }
            }
          },
          "400": {
            "description": "A status outside the enum"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-status",
        "summary": "Delete a session status",
        "description": "Delete a custom session status. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Status deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/statuses/{id}/restore": {
      "post": {
        "operationId": "restore-status",
        "summary": "Restore a deleted session status",
        "description": "Restore a previously soft-deleted session status. Requires the `write:metadata` scope.",
        "tags": [
          "Metadata Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Status restored",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionCustomStatus"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:metadata scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts": {
      "get": {
        "operationId": "list-agenda-drafts",
        "summary": "List agenda drafts",
        "description": "Returns all agenda drafts for an event.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/AgendaDraft"
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/create": {
      "post": {
        "operationId": "create-agenda-draft",
        "summary": "Create an agenda draft",
        "description": "Create a new agenda draft workspace. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string",
                    "description": "Draft name."
                  },
                  "description": {
                    "type": "string",
                    "description": "Optional description."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Draft created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AgendaDraft"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/{draftId}": {
      "get": {
        "operationId": "get-agenda-draft",
        "summary": "Get an agenda draft",
        "description": "Retrieve a single agenda draft by ID.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The draft ID."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AgendaDraft"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Draft not found"
          }
        }
      },
      "put": {
        "operationId": "update-agenda-draft",
        "summary": "Update an agenda draft",
        "description": "Update an agenda draft. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Draft updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AgendaDraft"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-agenda-draft",
        "summary": "Delete an agenda draft",
        "description": "Delete an agenda draft. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Draft deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/{draftId}/changes": {
      "get": {
        "operationId": "get-agenda-draft-changes",
        "summary": "Preview draft changes",
        "description": "Preview the pending changes in a draft before committing them to the live schedule.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "description": "A summary of additions, modifications, and removals."
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/{draftId}/commit": {
      "post": {
        "operationId": "commit-agenda-draft",
        "summary": "Commit an agenda draft",
        "description": "Apply all changes in the draft to the live event schedule. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Draft committed"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/{draftId}/sessions": {
      "get": {
        "operationId": "list-draft-sessions",
        "summary": "List draft sessions",
        "description": "List session placements within an agenda draft.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/DraftSession"
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/{draftId}/sessions/create": {
      "post": {
        "operationId": "create-draft-session",
        "summary": "Create a draft session",
        "description": "Place a session in an agenda draft. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "session_id"
                ],
                "properties": {
                  "session_id": {
                    "type": "string",
                    "format": "uuid"
                  },
                  "starts_at": {
                    "type": "string",
                    "format": "date-time"
                  },
                  "ends_at": {
                    "type": "string",
                    "format": "date-time"
                  },
                  "room_id": {
                    "type": "string",
                    "format": "uuid"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Draft session created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DraftSession"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/{draftId}/sessions/{draftSessionId}": {
      "put": {
        "operationId": "update-draft-session",
        "summary": "Update a draft session",
        "description": "Move or update a session placement in a draft. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "draftSessionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "starts_at": {
                    "type": "string",
                    "format": "date-time"
                  },
                  "ends_at": {
                    "type": "string",
                    "format": "date-time"
                  },
                  "room_id": {
                    "type": "string",
                    "format": "uuid"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Draft session updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DraftSession"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-draft-session",
        "summary": "Remove a draft session",
        "description": "Remove a session from an agenda draft. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "draftSessionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Draft session removed"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/agenda-drafts/{draftId}/sessions/bulk": {
      "post": {
        "operationId": "bulk-draft-sessions",
        "summary": "Bulk draft session operations",
        "description": "Batch create, update, or delete session placements in a draft. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "draftId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BulkOperations"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Bulk operation completed",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BulkResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/rules": {
      "get": {
        "operationId": "list-event-rules",
        "summary": "List event rules",
        "description": "Returns all scheduling rules for an event.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/EventRule"
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/rules/create": {
      "post": {
        "operationId": "create-event-rule",
        "summary": "Create an event rule",
        "description": "Create a scheduling constraint. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name",
                  "type"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "type": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true
                  },
                  "enabled": {
                    "type": "boolean",
                    "default": true
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Rule created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EventRule"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/rules/{ruleId}": {
      "get": {
        "operationId": "get-event-rule",
        "summary": "Get an event rule",
        "description": "Retrieve a single event rule by ID.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "ruleId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EventRule"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Rule not found"
          }
        }
      },
      "put": {
        "operationId": "update-event-rule",
        "summary": "Update an event rule",
        "description": "Update a scheduling rule. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "ruleId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true
                  },
                  "enabled": {
                    "type": "boolean"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Rule updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EventRule"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-event-rule",
        "summary": "Delete an event rule",
        "description": "Delete a scheduling rule. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "ruleId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Rule deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/personas": {
      "get": {
        "operationId": "list-personas",
        "summary": "List personas",
        "description": "Returns all evaluation personas for an event.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/Persona"
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/personas/create": {
      "post": {
        "operationId": "create-persona",
        "summary": "Create a persona",
        "description": "Create an attendee persona for schedule evaluation. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Persona created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Persona"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/personas/{personaId}": {
      "get": {
        "operationId": "get-persona",
        "summary": "Get a persona",
        "description": "Retrieve a single persona by ID.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "personaId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Persona"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Persona not found"
          }
        }
      },
      "put": {
        "operationId": "update-persona",
        "summary": "Update a persona",
        "description": "Update a persona. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "personaId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Persona updated",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Persona"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-persona",
        "summary": "Delete a persona",
        "description": "Delete a persona. Requires the `write:events` scope.",
        "tags": [
          "Agenda Planning"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "personaId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Persona deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/dashboards": {
      "get": {
        "operationId": "list-event-dashboards",
        "summary": "List dashboards",
        "description": "Returns all dashboards for an event. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "object",
                    "properties": {
                      "id": {
                        "type": "string"
                      },
                      "name": {
                        "type": "string"
                      },
                      "created_at": {
                        "type": "string",
                        "format": "date-time"
                      },
                      "updated_at": {
                        "type": "string",
                        "format": "date-time"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/dashboards/create": {
      "post": {
        "operationId": "create-event-dashboard",
        "summary": "Create a dashboard",
        "description": "Create a new dashboard with optional inline widgets. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  },
                  "widgets": {
                    "type": "array",
                    "items": {
                      "type": "object"
                    },
                    "description": "Optional inline widget definitions to create with the dashboard."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Dashboard created"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/dashboards/{id}": {
      "get": {
        "operationId": "get-event-dashboard",
        "summary": "Get a dashboard",
        "description": "Retrieve a dashboard with all widget data. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "id": {
                      "type": "string"
                    },
                    "name": {
                      "type": "string"
                    },
                    "widgets": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Dashboard not found"
          }
        }
      },
      "put": {
        "operationId": "update-event-dashboard",
        "summary": "Update a dashboard",
        "description": "Update dashboard properties. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Dashboard updated"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-event-dashboard",
        "summary": "Delete a dashboard",
        "description": "Delete a dashboard. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Dashboard deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/dashboards/{dashboardId}/widgets/create": {
      "post": {
        "operationId": "create-widget",
        "summary": "Create a widget",
        "description": "Add a widget to a dashboard. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "dashboardId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "type"
                ],
                "properties": {
                  "type": {
                    "type": "string",
                    "description": "Widget type (e.g., chart, table, number)."
                  },
                  "title": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Widget-specific configuration."
                  },
                  "query": {
                    "type": "string",
                    "description": "SbQL query for the widget data."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Widget created"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/widgets/{widgetId}": {
      "put": {
        "operationId": "update-widget",
        "summary": "Update a widget",
        "description": "Update widget configuration. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "widgetId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "title": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true
                  },
                  "query": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Widget updated"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-widget",
        "summary": "Delete a widget",
        "description": "Delete a widget from its dashboard. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "widgetId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Widget deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/queries": {
      "get": {
        "operationId": "list-event-queries",
        "summary": "List saved queries for an event",
        "description": "Returns saved SbQL queries scoped to an event. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "id": {
                            "type": "string"
                          },
                          "name": {
                            "type": "string"
                          },
                          "query": {
                            "type": "string"
                          },
                          "category": {
                            "type": "string"
                          }
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/event/{eventId}/queries/create": {
      "post": {
        "operationId": "create-event-query",
        "summary": "Create a saved query",
        "description": "Save a SbQL query as a reusable report. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name",
                  "query"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "query": {
                    "type": "string",
                    "description": "The SbQL query string."
                  },
                  "category": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Query saved"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/queries/{queryId}": {
      "put": {
        "operationId": "update-event-query",
        "summary": "Update a saved query",
        "description": "Update a saved query. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "query": {
                    "type": "string"
                  },
                  "category": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Query updated"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-event-query",
        "summary": "Delete a saved query",
        "description": "Delete a saved query. Requires the `write:events` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Query deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/queries/{queryId}/run": {
      "post": {
        "operationId": "run-event-query",
        "summary": "Run a saved query for an event",
        "description": "Execute a saved SbQL query. Requires the `write:events` scope (reports execute through the write pipeline for quota tracking).",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "obfuscatePii": {
                    "type": "boolean",
                    "default": true
                  },
                  "page": {
                    "type": "integer"
                  },
                  "limit": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Query not found"
          }
        }
      }
    },
    "/v1/dashboards": {
      "get": {
        "operationId": "list-org-dashboards-convenience",
        "summary": "List org dashboards (convenience)",
        "description": "Returns all dashboards across all events in the organization. Organization is resolved from the API token. No orgId required. Requires the `read:insights` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "object",
                    "properties": {
                      "id": {
                        "type": "string"
                      },
                      "name": {
                        "type": "string"
                      },
                      "event_id": {
                        "type": "integer",
                        "nullable": true
                      },
                      "created_at": {
                        "type": "string",
                        "format": "date-time"
                      },
                      "updated_at": {
                        "type": "string",
                        "format": "date-time"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/dashboards/create": {
      "post": {
        "operationId": "create-org-dashboard-convenience",
        "summary": "Create an org dashboard (convenience)",
        "description": "Create a new cross-event dashboard. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  },
                  "widgets": {
                    "type": "array",
                    "items": {
                      "type": "object"
                    },
                    "description": "Optional inline widget definitions."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Dashboard created"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/dashboards/{id}": {
      "get": {
        "operationId": "get-org-dashboard-convenience",
        "summary": "Get an org dashboard (convenience)",
        "description": "Retrieve a cross-event dashboard with all widget data. Organization is resolved from the API token. No orgId required. Requires the `read:insights` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "id": {
                      "type": "string"
                    },
                    "name": {
                      "type": "string"
                    },
                    "widgets": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Dashboard not found"
          }
        }
      },
      "put": {
        "operationId": "update-org-dashboard-convenience",
        "summary": "Update an org dashboard (convenience)",
        "description": "Update dashboard properties. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "description": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Dashboard updated"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-org-dashboard-convenience",
        "summary": "Delete an org dashboard (convenience)",
        "description": "Delete a cross-event dashboard. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Dashboard deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/dashboards/{dashboardId}/widgets/create": {
      "post": {
        "operationId": "create-org-widget-convenience",
        "summary": "Create an org widget (convenience)",
        "description": "Add a widget to an org-level dashboard. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "parameters": [
          {
            "name": "dashboardId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "type"
                ],
                "properties": {
                  "type": {
                    "type": "string",
                    "description": "Widget type (e.g., chart, table, number)."
                  },
                  "title": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true
                  },
                  "query": {
                    "type": "string",
                    "description": "SbQL query for the widget data."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Widget created"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/widgets/{widgetId}": {
      "put": {
        "operationId": "update-org-widget-convenience",
        "summary": "Update an org widget (convenience)",
        "description": "Update widget configuration. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "parameters": [
          {
            "name": "widgetId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "title": {
                    "type": "string"
                  },
                  "config": {
                    "type": "object",
                    "additionalProperties": true
                  },
                  "query": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Widget updated"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-org-widget-convenience",
        "summary": "Delete an org widget (convenience)",
        "description": "Delete a widget. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Dashboards & Widgets"
        ],
        "parameters": [
          {
            "name": "widgetId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Widget deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/queries": {
      "get": {
        "operationId": "list-org-queries-convenience",
        "summary": "List org saved queries (convenience)",
        "description": "Returns all saved SbQL queries across the organization. Organization is resolved from the API token. No orgId required. Requires the `read:insights` scope.",
        "tags": [
          "Reports & Queries"
        ],
        "parameters": [
          {
            "name": "category",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Filter by category."
          },
          {
            "name": "page",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "id": {
                            "type": "string"
                          },
                          "name": {
                            "type": "string"
                          },
                          "query": {
                            "type": "string"
                          },
                          "category": {
                            "type": "string"
                          },
                          "event_id": {
                            "type": "integer",
                            "nullable": true
                          }
                        }
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/v1/queries/create": {
      "post": {
        "operationId": "create-org-query-convenience",
        "summary": "Create an org saved query (convenience)",
        "description": "Save a cross-event SbQL query. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Reports & Queries"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name",
                  "query"
                ],
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "query": {
                    "type": "string",
                    "description": "The SbQL query string."
                  },
                  "category": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Query saved"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/queries/{queryId}": {
      "put": {
        "operationId": "update-org-query-convenience",
        "summary": "Update an org saved query (convenience)",
        "description": "Update a saved query. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Reports & Queries"
        ],
        "parameters": [
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "query": {
                    "type": "string"
                  },
                  "category": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Query updated"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-org-query-convenience",
        "summary": "Delete an org saved query (convenience)",
        "description": "Delete a saved query. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope.",
        "tags": [
          "Reports & Queries"
        ],
        "parameters": [
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Query deleted"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:events scope"
          }
        }
      }
    },
    "/v1/queries/{queryId}/run": {
      "post": {
        "operationId": "run-org-query-convenience",
        "summary": "Run an org saved query (convenience)",
        "description": "Execute a saved cross-event SbQL query. Organization is resolved from the API token. No orgId required. Requires the `write:events` scope (reports execute through the write pipeline for quota tracking).",
        "tags": [
          "Reports & Queries"
        ],
        "parameters": [
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "obfuscatePii": {
                    "type": "boolean",
                    "default": true
                  },
                  "page": {
                    "type": "integer"
                  },
                  "limit": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Query not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/insights/execute": {
      "post": {
        "operationId": "execute-event-query",
        "summary": "Execute a SbQL query (event-scoped)",
        "description": "Execute a SbQL query scoped to a specific event. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID to scope the query to."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "query"
                ],
                "properties": {
                  "query": {
                    "type": "string"
                  },
                  "obfuscatePii": {
                    "type": "boolean",
                    "default": true
                  },
                  "page": {
                    "type": "integer"
                  },
                  "limit": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid query"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/insights/ai/generate": {
      "post": {
        "operationId": "generate-event-query",
        "summary": "Generate a SbQL query from natural language (event-scoped)",
        "description": "Use AI to translate natural language into a SbQL query scoped to a specific event. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "prompt"
                ],
                "properties": {
                  "prompt": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "query": {
                      "type": "string"
                    },
                    "explanation": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/insights/schema": {
      "get": {
        "operationId": "get-event-insights-schema",
        "summary": "Get event-scoped insights schema",
        "description": "Returns the SbQL schema including event-specific custom fields. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/insights/suggestions": {
      "get": {
        "operationId": "get-event-suggestions",
        "summary": "Get event-scoped query suggestions",
        "description": "Returns contextual query suggestions for a specific event. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "suggestions": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "query": {
                            "type": "string"
                          },
                          "description": {
                            "type": "string"
                          }
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/insights/queries": {
      "get": {
        "operationId": "list-event-insights-queries",
        "summary": "List saved queries (event-scoped insights)",
        "description": "Returns saved queries via the insights proxy. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/insights/queries/{queryId}/run": {
      "post": {
        "operationId": "run-event-insights-query",
        "summary": "Run a saved query (event-scoped insights)",
        "description": "Execute a saved query via the insights proxy. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/insights/dashboards/{id}": {
      "get": {
        "operationId": "get-event-insights-dashboard",
        "summary": "Get a dashboard (event-scoped insights)",
        "description": "Retrieve a dashboard via the insights proxy. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "id": {
                      "type": "string"
                    },
                    "name": {
                      "type": "string"
                    },
                    "widgets": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/gdpr/requests": {
      "get": {
        "operationId": "list-gdpr-requests",
        "summary": "List GDPR requests",
        "description": "Returns the organization's GDPR data access and erasure requests,\nnewest first.\n\nThe response is a bare JSON array, not a `results` envelope. This page\npreviously showed an envelope; the endpoint has always returned the\narray.\n\nPaginated with `page` and `pageSize` (default 25, maximum 100). Keep\nrequesting pages until one comes back with fewer than `pageSize`\nentries.\n\nBoth parameters are validated. A `page` or `pageSize` outside its\ndocumented range, and any query parameter this operation does not\ndeclare, are rejected with a `400`. Out-of-range values used to be\naccepted and silently clamped.\n",
        "tags": [
          "GDPR"
        ],
        "parameters": [
          {
            "name": "page",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 999,
              "default": 1
            },
            "description": "1-based page number, 1 to 999. Outside that range is a `400`."
          },
          {
            "name": "pageSize",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            },
            "description": "Requests per page, 1 to 100. Outside that range is a `400`; values above 100 are no longer clamped."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/GDPRRequest"
                  }
                }
              }
            }
          },
          "400": {
            "description": "`page` or `pageSize` is outside its documented range, or an undeclared query parameter was sent."
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      },
      "post": {
        "operationId": "create-gdpr-request",
        "summary": "Create a GDPR request",
        "description": "Submit a GDPR data access or erasure request for one email address, and\nprocess it synchronously against the organization's data.\n\nFor `requestType: erasure` the call returns once the erasure has run.\nRead `status` to find out what happened — it is recorded by the\nerasure itself and is never assumed:\n\n- `complete` — the email matched at least one record and erasure ran\n  against it.\n- `no_records_found` — nothing in this organization matched the email.\n  Nothing was erased. Treat this as an outcome to escalate, not a\n  fulfilled request.\n\n`response` carries the identifiers that were matched, and on requests\nprocessed recently also `counts`, `users_scrubbed` and\n`users_retained` — the compliance evidence of what the erasure actually\ndid. A user account shared with another organization is retained rather\nthan scrubbed, and appears in `users_retained`.\n\nA `502` means the erasure did not run and **nothing was recorded or\nerased**; retry the request.\n",
        "tags": [
          "GDPR"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "requestType",
                  "identityType",
                  "identityValue"
                ],
                "properties": {
                  "requestType": {
                    "type": "string",
                    "enum": [
                      "erasure",
                      "access"
                    ],
                    "description": "The type of GDPR request."
                  },
                  "identityType": {
                    "type": "string",
                    "enum": [
                      "email"
                    ],
                    "description": "The type of identity to look up."
                  },
                  "identityValue": {
                    "type": "string",
                    "description": "The identity value (e.g., an email address).",
                    "examples": [
                      "jane.doe@example.com"
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The request was recorded and, for an erasure, processed. Check `status` for the outcome.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/GDPRRequest"
                }
              }
            }
          },
          "400": {
            "description": "Bad request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "502": {
            "description": "The erasure service could not be reached. Nothing was recorded and nothing was erased — retry."
          }
        }
      }
    },
    "/v1/insights/execute": {
      "post": {
        "operationId": "execute-query",
        "summary": "Execute a SbQL query",
        "description": "Execute a SbQL query against event data and return results. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "query"
                ],
                "properties": {
                  "query": {
                    "type": "string",
                    "description": "The SbQL query string to execute.",
                    "examples": [
                      "SELECT sessions.title, sessions.status FROM sessions"
                    ]
                  },
                  "eventId": {
                    "type": "integer",
                    "description": "Scope query to a single event."
                  },
                  "eventIds": {
                    "type": "array",
                    "items": {
                      "type": "integer"
                    },
                    "description": "Scope query to multiple events."
                  },
                  "obfuscatePii": {
                    "type": "boolean",
                    "default": true,
                    "description": "Whether to obfuscate personally identifiable information in results."
                  },
                  "format": {
                    "type": "string",
                    "description": "Output format for results."
                  },
                  "page": {
                    "type": "integer",
                    "description": "Page number for paginated results."
                  },
                  "limit": {
                    "type": "integer",
                    "description": "Maximum number of rows to return."
                  },
                  "search": {
                    "type": "string",
                    "description": "Full-text search within results."
                  },
                  "sortBy": {
                    "type": "string",
                    "description": "Column name to sort results by."
                  },
                  "sortDirection": {
                    "type": "string",
                    "enum": [
                      "asc",
                      "desc"
                    ],
                    "description": "Sort direction."
                  },
                  "groupBy": {
                    "type": "string",
                    "description": "Column name to group results by."
                  },
                  "pivot": {
                    "type": "string",
                    "description": "Column name to pivot results on."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid query"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/insights/ai/generate": {
      "post": {
        "operationId": "generate-query",
        "summary": "Generate a SbQL query from natural language",
        "description": "Use AI to translate a natural language prompt into a SbQL query. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "prompt"
                ],
                "properties": {
                  "prompt": {
                    "type": "string",
                    "description": "Natural language description of the data you want to query.",
                    "examples": [
                      "Show me all accepted sessions with their speakers"
                    ]
                  },
                  "eventId": {
                    "type": "integer",
                    "description": "Scope to a single event for context."
                  },
                  "eventIds": {
                    "type": "array",
                    "items": {
                      "type": "integer"
                    },
                    "description": "Scope to multiple events for context."
                  },
                  "conversationHistory": {
                    "type": "array",
                    "items": {
                      "type": "object",
                      "properties": {
                        "role": {
                          "type": "string",
                          "description": "The message role (e.g., user, assistant)."
                        },
                        "content": {
                          "type": "string",
                          "description": "The message content."
                        }
                      }
                    },
                    "description": "Previous conversation turns for multi-turn query refinement."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "query": {
                      "type": "string",
                      "description": "The generated SbQL query."
                    },
                    "explanation": {
                      "type": "string",
                      "description": "Human-readable explanation of the generated query."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/insights/schema": {
      "get": {
        "operationId": "get-schema",
        "summary": "Get insights schema",
        "description": "Returns the SbQL schema for the organization, including available entities and fields. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "description": "The SbQL schema definition."
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/insights/events/{eventId}/schema": {
      "get": {
        "operationId": "get-event-schema",
        "summary": "Get event-specific insights schema",
        "description": "Returns the SbQL schema scoped to a specific event, including event-specific custom fields. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "description": "The event-scoped SbQL schema definition."
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/insights/suggestions": {
      "get": {
        "operationId": "get-suggestions",
        "summary": "Get query suggestions",
        "description": "Returns contextual SbQL query suggestions. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer"
            },
            "description": "Scope suggestions to a specific event."
          },
          {
            "name": "category",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Filter suggestions by category."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "suggestions": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "query": {
                            "type": "string"
                          },
                          "description": {
                            "type": "string"
                          },
                          "category": {
                            "type": "string"
                          }
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/insights/queries": {
      "get": {
        "operationId": "list-queries",
        "summary": "List saved queries",
        "description": "Returns a list of saved SbQL queries. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer"
            },
            "description": "Filter queries by event."
          },
          {
            "name": "category",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Filter queries by category."
          },
          {
            "name": "page",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer"
            },
            "description": "Page number."
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer"
            },
            "description": "Results per page."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "id": {
                            "type": "string"
                          },
                          "name": {
                            "type": "string"
                          },
                          "query": {
                            "type": "string"
                          },
                          "category": {
                            "type": "string"
                          },
                          "eventId": {
                            "type": "integer"
                          }
                        }
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          }
        }
      }
    },
    "/v1/insights/queries/{queryId}/run": {
      "post": {
        "operationId": "run-query",
        "summary": "Run a saved query",
        "description": "Execute a previously saved SbQL query by ID. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "name": "queryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The saved query ID."
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "eventId": {
                    "type": "integer",
                    "description": "Override the event scope for this run."
                  },
                  "eventIds": {
                    "type": "array",
                    "items": {
                      "type": "integer"
                    },
                    "description": "Override with multiple event scopes."
                  },
                  "obfuscatePii": {
                    "type": "boolean",
                    "default": true
                  },
                  "format": {
                    "type": "string"
                  },
                  "page": {
                    "type": "integer"
                  },
                  "limit": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/Pagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          },
          "404": {
            "description": "Saved query not found"
          }
        }
      }
    },
    "/v1/insights/dashboards/{id}": {
      "get": {
        "operationId": "get-dashboard",
        "summary": "Get a dashboard",
        "description": "Retrieve a dashboard with all its widget data. Requires the `read:insights` scope.",
        "tags": [
          "Insights"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The dashboard ID."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "id": {
                      "type": "string"
                    },
                    "name": {
                      "type": "string"
                    },
                    "widgets": {
                      "type": "array",
                      "items": {
                        "type": "object"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope"
          },
          "404": {
            "description": "Dashboard not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/create": {
      "post": {
        "operationId": "create-session",
        "summary": "Create a session",
        "description": "Create a new session in an event. Requires the `write:sessions` scope. Subject to rate limiting (100 req/15min) and daily write quota (10,000/day per token).",
        "tags": [
          "Session Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "title"
                ],
                "properties": {
                  "title": {
                    "type": "string",
                    "description": "Session title."
                  },
                  "description": {
                    "type": "string",
                    "description": "Session description (HTML allowed)."
                  },
                  "starts_at": {
                    "type": "string",
                    "format": "date-time",
                    "description": "Session start time."
                  },
                  "ends_at": {
                    "type": "string",
                    "format": "date-time",
                    "description": "Session end time."
                  },
                  "capacity": {
                    "type": "integer",
                    "description": "Maximum capacity for the session."
                  },
                  "room_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Room ID to assign."
                  },
                  "track_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Track ID to assign."
                  },
                  "level_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Level ID to assign."
                  },
                  "format_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Format ID to assign."
                  },
                  "language_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Language ID to assign."
                  },
                  "parent_session_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Parent session ID (for subsessions)."
                  },
                  "tag_ids": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "format": "uuid"
                    },
                    "description": "Tag IDs to assign."
                  },
                  "status": {
                    "type": "string",
                    "description": "Session status (e.g., pending, accepted)."
                  },
                  "is_public": {
                    "type": "boolean",
                    "description": "Whether the session is publicly visible."
                  },
                  "is_abstract": {
                    "type": "boolean",
                    "default": false,
                    "description": "Create an abstract (CFP) submission instead of a program session.\nRequires the Sessions 2.0 feature on the event.\n"
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Session created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Session"
                }
              }
            }
          },
          "400": {
            "description": "Validation error"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope or feature not enabled"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/restore": {
      "post": {
        "operationId": "restore-session",
        "summary": "Restore a deleted session",
        "description": "Restore a previously soft-deleted session. Requires the `write:sessions` scope.",
        "tags": [
          "Session Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sessionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The session ID."
          }
        ],
        "responses": {
          "200": {
            "description": "Session restored",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Session"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "Session not found or not deleted"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/bulk": {
      "post": {
        "operationId": "bulk-sessions",
        "summary": "Bulk session operations",
        "description": "Create, update, or delete multiple sessions in a single request (max 100 operations). Requires the `write:sessions` scope.",
        "tags": [
          "Session Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BulkOperations"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Bulk operation completed",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BulkResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/contacts/create": {
      "post": {
        "operationId": "create-contact",
        "summary": "Create a contact",
        "description": "Create a new contact in an event. Requires the `write:contacts` scope. Subject to rate limiting (100 req/15min) and daily write quota (10,000/day per token).",
        "tags": [
          "Contact Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "email"
                ],
                "properties": {
                  "email": {
                    "type": "string",
                    "format": "email",
                    "description": "Contact email address (required, must be unique within the event)."
                  },
                  "first_name": {
                    "type": "string",
                    "description": "First name."
                  },
                  "last_name": {
                    "type": "string",
                    "description": "Last name."
                  },
                  "company": {
                    "type": "string",
                    "description": "Company or organization name."
                  },
                  "title": {
                    "type": "string",
                    "description": "Job title."
                  },
                  "phone": {
                    "type": "string",
                    "description": "Phone number."
                  },
                  "about": {
                    "type": "string",
                    "description": "Biography. HTML is allowed and stored as rich text."
                  },
                  "salutation": {
                    "type": "string"
                  },
                  "honorific": {
                    "type": "string"
                  },
                  "address_line_1": {
                    "type": "string"
                  },
                  "address_line_2": {
                    "type": "string"
                  },
                  "address_city": {
                    "type": "string"
                  },
                  "address_state": {
                    "type": "string"
                  },
                  "address_postal_code": {
                    "type": "string"
                  },
                  "address_country": {
                    "type": "string",
                    "description": "ISO 3166-1 numeric code (as GET returns), alpha-2 or alpha-3 code, or English country name. Stored and returned as the numeric code. An unknown value returns `400` naming the field and nothing is written."
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Contact created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Contact"
                }
              }
            }
          },
          "400": {
            "description": "Validation error"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope or feature not enabled"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/contacts/{contactId}/restore": {
      "post": {
        "operationId": "restore-contact",
        "summary": "Restore a deleted contact",
        "description": "Restore a previously soft-deleted contact. Requires the `write:contacts` scope.",
        "tags": [
          "Contact Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The contact ID."
          }
        ],
        "responses": {
          "200": {
            "description": "Contact restored",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Contact"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:contacts scope"
          },
          "404": {
            "description": "Contact not found or not deleted"
          }
        }
      }
    },
    "/v1/event/{eventId}/contacts/bulk": {
      "post": {
        "operationId": "bulk-contacts",
        "summary": "Bulk contact operations",
        "description": "Create, update, or delete multiple contacts in a single request (max\n100 operations). Requires the `write:contacts` scope.\n\nSend the `{ action, id, data }` envelope every other bulk endpoint\nuses. This endpoint previously read the contact fields off the\noperation itself and rejected the documented envelope with\n`email is required` on every action; that is fixed, and the flat form\nbelow is still accepted for existing integrations.\n\nOperations are applied **in request order, one transaction each**. An\noperation that fails leaves nothing behind — no partially written\ncontact, no dangling event association — and the operations around it\nstill apply. `results` comes back in request order, so\n`results[i]` always describes `operations[i]`.\n\n`data` accepts the same fields as `POST /contacts/create`, including\n`custom_fields` and `translated_fields`. A create whose email already\nexists in the organization links that contact to the event instead of\nduplicating it, and reports `status: \"associated\"`.\n\n<Warning>\n  **Deprecated: flat operations.** An operation with no `action` key is\n  treated as a create, with the operation object itself as its `data`:\n  `{ \"email\": \"a@b.com\", \"first_name\": \"Ada\" }` behaves like\n  `{ \"action\": \"create\", \"data\": { \"email\": \"a@b.com\", \"first_name\": \"Ada\" } }`.\n  This shape is supported for existing callers only and will not gain\n  new capabilities. Send the envelope.\n</Warning>\n",
        "tags": [
          "Contact Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BulkOperations"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Bulk operation completed",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BulkResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:contacts scope"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/exhibitors/create": {
      "post": {
        "operationId": "create-exhibitor",
        "summary": "Create an exhibitor",
        "description": "Create a new exhibitor in an event. Requires the `write:exhibitors` scope. Subject to rate limiting (100 req/15min) and daily write quota (10,000/day per token).",
        "tags": [
          "Exhibitor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string",
                    "description": "Exhibitor name. Required if `account_id` is not provided."
                  },
                  "account_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Existing account ID to link, instead of creating a new account. Required if `name` is not provided. This is also how a group takes its second role: pass the `account_id` of a record that is already a sponsor or an exhibitor and it holds both roles on this event, under the same id. Repeating a link it already holds is a no-op.\n"
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Exhibitor created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Exhibitor"
                }
              }
            }
          },
          "400": {
            "description": "Validation error"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope or feature not enabled"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/exhibitors/{exhibitorId}/restore": {
      "post": {
        "operationId": "restore-exhibitor",
        "summary": "Restore a deleted exhibitor",
        "description": "Restore a previously soft-deleted exhibitor. Requires the `write:exhibitors` scope.\n\nRestore has the same reach as the delete it reverses: it restores the **group**, so a group that held both roles comes back as both a sponsor and an exhibitor, and it reappears on every event it was linked to — not only the event in the path.\n",
        "tags": [
          "Exhibitor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "exhibitorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The exhibitor ID."
          }
        ],
        "responses": {
          "200": {
            "description": "Exhibitor restored",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Exhibitor"
                }
              }
            }
          },
          "400": {
            "description": "The exhibitor is not deleted, so there is nothing to restore. Restore is not idempotent — check before retrying.\n"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:exhibitors scope"
          },
          "404": {
            "description": "No exhibitor with this id on this event. A record that exists but does not hold the exhibitor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds.\n"
          }
        }
      }
    },
    "/v1/event/{eventId}/exhibitors/bulk": {
      "post": {
        "operationId": "bulk-exhibitors",
        "summary": "Bulk exhibitor operations",
        "description": "Create, update, or delete multiple exhibitors in a single request (max 100 operations). Requires the `write:exhibitors` scope.",
        "tags": [
          "Exhibitor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BulkOperations"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Bulk operation completed",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BulkResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:exhibitors scope"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/sponsors/create": {
      "post": {
        "operationId": "create-sponsor",
        "summary": "Create a sponsor",
        "description": "Create a new sponsor in an event. Requires the `write:sponsors` scope. Subject to rate limiting (100 req/15min) and daily write quota (10,000/day per token).",
        "tags": [
          "Sponsor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string",
                    "description": "Sponsor name. Required if `account_id` is not provided."
                  },
                  "account_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Existing account ID to link, instead of creating a new account. Required if `name` is not provided. This is also how a group takes its second role: pass the `account_id` of a record that is already a sponsor or an exhibitor and it holds both roles on this event, under the same id. Repeating a link it already holds is a no-op.\n"
                  },
                  "custom_fields": {
                    "type": "object",
                    "additionalProperties": true,
                    "description": "Custom field values keyed by field internal name.\n\nFor `number`, `currency`, and `percent` fields, an empty\nstring (`\"\"`) clears the stored value — identical to\nsending `null`. `0` and `\"0\"` store an actual zero.\n\nFor `checkbox` fields, send boolean `true` or `false`.\nOn read, a checked box serializes as the string `\"Yes\"`, an\nexplicitly unchecked one as `\"No\"`, and a box that was never\nset as `null`.\n\nFields owned by an integration (for example\n`swoogo_session_id`, `cvent_session_id`,\n`visit_session_id`) are hydrated by the connector and\nreject writes with `400` `FIELD_READ_ONLY`, naming the\nfield in `details.field`. Omit them from `custom_fields`.\n"
                  },
                  "translated_fields": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/TranslatedFieldWrite"
                    },
                    "description": "Language variants to write using the same shape returned on reads.\nOmit this key on update to leave existing translations unchanged.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Sponsor created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Sponsor"
                }
              }
            }
          },
          "400": {
            "description": "Validation error"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Insufficient scope or feature not enabled"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/sponsors/{sponsorId}/restore": {
      "post": {
        "operationId": "restore-sponsor",
        "summary": "Restore a deleted sponsor",
        "description": "Restore a previously soft-deleted sponsor. Requires the `write:sponsors` scope.\n\nRestore has the same reach as the delete it reverses: it restores the **group**, so a group that held both roles comes back as both a sponsor and an exhibitor, and it reappears on every event it was linked to — not only the event in the path.\n",
        "tags": [
          "Sponsor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          },
          {
            "name": "sponsorId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "The sponsor ID."
          }
        ],
        "responses": {
          "200": {
            "description": "Sponsor restored",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Sponsor"
                }
              }
            }
          },
          "400": {
            "description": "The sponsor is not deleted, so there is nothing to restore. Restore is not idempotent — check before retrying.\n"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sponsors scope"
          },
          "404": {
            "description": "No sponsor with this id on this event. A record that exists but does not hold the sponsor role — a contact, or a group linked only as the other role — is also a `404` here; look it up on the endpoint for the role it holds.\n"
          }
        }
      }
    },
    "/v1/event/{eventId}/sponsors/bulk": {
      "post": {
        "operationId": "bulk-sponsors",
        "summary": "Bulk sponsor operations",
        "description": "Create, update, or delete multiple sponsors in a single request (max 100 operations). Requires the `write:sponsors` scope.",
        "tags": [
          "Sponsor Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "The event ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BulkOperations"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Bulk operation completed",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BulkResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:sponsors scope"
          },
          "429": {
            "description": "Rate limit or daily quota exceeded"
          }
        }
      }
    },
    "/v1/event/{eventId}/fields/create": {
      "post": {
        "operationId": "create-field",
        "summary": "Create a custom field",
        "description": "Create a new custom field for an event module. Requires the `write:fields` scope.",
        "tags": [
          "Field Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string"
                  },
                  "type": {
                    "type": "string"
                  },
                  "module_id": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Field created"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Missing write:fields scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/fields/{fieldId}": {
      "put": {
        "operationId": "update-field",
        "summary": "Update a custom field",
        "tags": [
          "Field Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "fieldId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Field updated"
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      },
      "delete": {
        "operationId": "delete-field",
        "summary": "Delete a custom field",
        "tags": [
          "Field Writes"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "fieldId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Field deleted. No response body."
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/oauth/authorize": {
      "get": {
        "operationId": "oauth-authorize",
        "summary": "Validate authorization request",
        "description": "Validates OAuth authorization request parameters (client_id, redirect_uri, scopes, PKCE challenge). Returns the validated request for display on the consent page. No authentication required.",
        "tags": [
          "OAuth"
        ],
        "security": [],
        "parameters": [
          {
            "name": "client_id",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "redirect_uri",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "response_type",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "enum": [
                "code"
              ]
            }
          },
          {
            "name": "code_challenge",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "code_challenge_method",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "enum": [
                "S256"
              ]
            }
          },
          {
            "name": "scope",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Space-separated scopes"
          },
          {
            "name": "state",
            "in": "query",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Authorization request validated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "authorization_request": {
                      "type": "object",
                      "properties": {
                        "client_id": {
                          "type": "string"
                        },
                        "client_name": {
                          "type": "string"
                        },
                        "redirect_uri": {
                          "type": "string"
                        },
                        "scopes": {
                          "type": "array",
                          "items": {
                            "type": "string"
                          }
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid request parameters"
          }
        }
      }
    },
    "/oauth/token": {
      "post": {
        "operationId": "oauth-token",
        "summary": "Exchange code for tokens",
        "description": "Exchange an authorization code for access and refresh tokens (authorization_code grant), or refresh an expired access token (refresh_token grant). Uses PKCE verification — no client secret required.",
        "tags": [
          "OAuth"
        ],
        "security": [],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "oneOf": [
                  {
                    "type": "object",
                    "title": "Authorization Code Exchange",
                    "required": [
                      "grant_type",
                      "code",
                      "redirect_uri",
                      "client_id",
                      "code_verifier"
                    ],
                    "properties": {
                      "grant_type": {
                        "type": "string",
                        "enum": [
                          "authorization_code"
                        ]
                      },
                      "code": {
                        "type": "string"
                      },
                      "redirect_uri": {
                        "type": "string"
                      },
                      "client_id": {
                        "type": "string"
                      },
                      "code_verifier": {
                        "type": "string",
                        "description": "PKCE code verifier"
                      }
                    }
                  },
                  {
                    "type": "object",
                    "title": "Refresh Token",
                    "required": [
                      "grant_type",
                      "refresh_token",
                      "client_id"
                    ],
                    "properties": {
                      "grant_type": {
                        "type": "string",
                        "enum": [
                          "refresh_token"
                        ]
                      },
                      "refresh_token": {
                        "type": "string"
                      },
                      "client_id": {
                        "type": "string"
                      }
                    }
                  }
                ]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Tokens issued",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "access_token": {
                      "type": "string"
                    },
                    "token_type": {
                      "type": "string",
                      "example": "Bearer"
                    },
                    "expires_in": {
                      "type": "integer",
                      "example": 3600
                    },
                    "refresh_token": {
                      "type": "string"
                    },
                    "scope": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid grant or parameters"
          }
        }
      }
    },
    "/oauth/revoke": {
      "post": {
        "operationId": "oauth-revoke",
        "summary": "Revoke a token",
        "description": "Revoke an access or refresh token. Conforms to RFC 7009. Always returns 200 regardless of whether the token was found.",
        "tags": [
          "OAuth"
        ],
        "security": [],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "token"
                ],
                "properties": {
                  "token": {
                    "type": "string"
                  },
                  "token_type_hint": {
                    "type": "string",
                    "enum": [
                      "access_token",
                      "refresh_token"
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Token revoked (or was already invalid)"
          }
        }
      }
    },
    "/oauth/.well-known/oauth-authorization-server": {
      "get": {
        "operationId": "oauth-metadata",
        "summary": "Authorization server metadata",
        "description": "Returns OAuth 2.0 Authorization Server Metadata per RFC 8414. Includes supported scopes, grant types, and endpoint URLs.",
        "tags": [
          "OAuth"
        ],
        "security": [],
        "responses": {
          "200": {
            "description": "Server metadata",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "issuer": {
                      "type": "string"
                    },
                    "authorization_endpoint": {
                      "type": "string"
                    },
                    "token_endpoint": {
                      "type": "string"
                    },
                    "revocation_endpoint": {
                      "type": "string"
                    },
                    "response_types_supported": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    "grant_types_supported": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    "scopes_supported": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    "code_challenge_methods_supported": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/v1/event/{eventId}/contacts/{contactId}/sessions": {
      "get": {
        "operationId": "get-contact-sessions",
        "summary": "Get a contact's sessions",
        "description": "Returns all sessions associated with a specific contact within an\nevent, including linked composition sources. Each session summary\nincludes `is_abstract` and `composition_status`. The full\n`composition` graph is not available on this lightweight endpoint —\nuse session GET or search with `expand=composition` for details.\n",
        "tags": [
          "Contacts"
        ],
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ContactSessionsResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Contact not found"
          }
        }
      }
    },
    "/v1/organization/{orgId}/contacts/{contactId}/sessions": {
      "get": {
        "operationId": "get-org-contact-sessions",
        "summary": "Get an org contact's sessions",
        "description": "Returns all sessions associated with a specific contact across the\norganization, including linked composition sources. Each session\nsummary includes `is_abstract`, `composition_status`, and\n`event_id`. The full `composition` graph is not available on this\nlightweight endpoint.\n",
        "tags": [
          "Contacts"
        ],
        "parameters": [
          {
            "name": "orgId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "contactId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/OrgContactSessionsResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Contact not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/content": {
      "get": {
        "operationId": "list-event-content",
        "summary": "List composed session content for an event",
        "description": "Paginated list of session content packs (composed transcript, preferred summary,\ninsights, podcast status, and document links). Prefer this over the raw\npolymorphic transcriptions list for mobile and partner apps.\n\nRequires `read:transcriptions` scope (legacy tokens with empty scopes pass).\n\nDefault packs are compact (`elements` empty on transcription items). Pass\n`expand=items` (plus other types) for full element arrays.\n",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          },
          {
            "name": "session_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "expand",
            "in": "query",
            "description": "Comma-separated item types. Default `transcription,summary,insight,podcast,document`.\nAdd `items` on the event list for full transcription elements (list is compact by default).\n`expand=items` alone still includes the default types. Session GET always returns full elements.\n",
            "schema": {
              "type": "string",
              "example": "transcription,summary,items"
            }
          },
          {
            "name": "interval_sec",
            "in": "query",
            "description": "Optional time window (seconds) for rechunking same-speaker transcript elements. Omit for speaker turns only. Clamped to 3600.",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 3600
            }
          },
          {
            "name": "provider",
            "in": "query",
            "description": "Preferred summary provider when multiple exist.",
            "schema": {
              "type": "string",
              "enum": [
                "claude",
                "openai"
              ]
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionContentListResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/content/event": {
      "get": {
        "operationId": "get-event-content",
        "summary": "Get event-level content artifacts",
        "description": "Event report document metadata and recap rollup (quotes, topics, summary excerpts).\nRequires `read:transcriptions` scope. Default expand is `document,recap`.\n",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "name": "expand",
            "in": "query",
            "description": "Comma-separated. Default `document,recap`. Pass only the types you want.",
            "schema": {
              "type": "string",
              "example": "document,recap"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EventContentResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/content/items/{itemId}": {
      "get": {
        "operationId": "get-content-item",
        "summary": "Get a single content item",
        "description": "Resolve one content item. `itemId` may be a session UUID (composed transcription),\na summary/insight/podcast UUID, or a document type (`summary_pdf`, `summary_card`,\n`event_report`, `recap`). Document types `summary_pdf` / `summary_card` require\n`session_id`. Requires `read:transcriptions` scope.\n",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "name": "itemId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "session_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "interval_sec",
            "in": "query",
            "schema": {
              "type": "integer",
              "minimum": 1
            }
          },
          {
            "name": "provider",
            "in": "query",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ContentItemResponse"
                }
              }
            }
          },
          "400": {
            "description": "Validation error"
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          },
          "404": {
            "description": "Not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/content/documents/{documentType}": {
      "get": {
        "operationId": "download-event-content-document",
        "summary": "Download an event content document",
        "description": "Streams `event_report` PDF. Requires `read:transcriptions` scope.",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "name": "documentType",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "enum": [
                "event_report"
              ]
            }
          },
          {
            "name": "variant",
            "in": "query",
            "schema": {
              "type": "string",
              "enum": [
                "full",
                "daily",
                "theme"
              ],
              "default": "full"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "PDF bytes",
            "content": {
              "application/pdf": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          },
          "404": {
            "description": "Not available"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/content": {
      "get": {
        "operationId": "get-session-content",
        "summary": "Get composed content for a session",
        "description": "Canonical one-call session pack for mobile and partner apps — composed\ntranscription elements, preferred summary, insights, podcast URL/status,\nand summary PDF/card links. Distinct from session **composition**\n(abstract/parent-child linking).\n\nRequires `read:transcriptions` scope (legacy tokens with empty scopes pass).\n",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "expand",
            "in": "query",
            "description": "Comma-separated item types. Default `transcription,summary,insight,podcast,document`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "interval_sec",
            "in": "query",
            "description": "Optional time window (seconds) for rechunking same-speaker elements.",
            "schema": {
              "type": "integer",
              "minimum": 1
            }
          },
          {
            "name": "provider",
            "in": "query",
            "schema": {
              "type": "string",
              "enum": [
                "claude",
                "openai"
              ]
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionContentResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          },
          "404": {
            "description": "Session not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/content/documents/{documentType}": {
      "get": {
        "operationId": "download-session-content-document",
        "summary": "Download a session content document",
        "description": "Streams `summary_pdf` or `summary_card`. Requires `read:transcriptions` scope.",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "documentType",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "enum": [
                "summary_pdf",
                "summary_card"
              ]
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Document bytes",
            "content": {
              "application/pdf": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "image/png": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          },
          "404": {
            "description": "Not available"
          }
        }
      }
    },
    "/v1/event/{eventId}/transcriptions": {
      "get": {
        "operationId": "list-event-transcriptions",
        "summary": "List transcriptions for an event",
        "description": "Paginated list of transcription artifacts across all sessions. Filter by type, session_id, or language_code. Requires `read:transcriptions` scope (legacy tokens with empty scopes pass). Prefer `/content` for composed mobile-friendly packs.",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          },
          {
            "name": "type",
            "in": "query",
            "schema": {
              "type": "string",
              "enum": [
                "fragment",
                "summary",
                "insight",
                "translation"
              ]
            }
          },
          {
            "name": "session_id",
            "in": "query",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "language_code",
            "in": "query",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "include_partial",
            "in": "query",
            "schema": {
              "type": "boolean",
              "default": false
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TranscriptionListResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/transcriptions/{transcriptionId}": {
      "get": {
        "operationId": "get-transcription",
        "summary": "Get a transcription by ID",
        "description": "Requires `read:transcriptions` scope (legacy tokens with empty scopes pass).",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "name": "transcriptionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TranscriptionResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          },
          "404": {
            "description": "Not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/transcriptions": {
      "get": {
        "operationId": "list-session-transcriptions",
        "summary": "List transcriptions for a session",
        "description": "Requires `read:transcriptions` scope (legacy tokens with empty scopes pass).",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/PageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TranscriptionListResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          }
        }
      },
      "post": {
        "operationId": "create-transcription",
        "summary": "Create a transcription artifact",
        "description": "Requires `write:transcriptions` scope.",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/TranscriptionCreateRequest"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TranscriptionResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing write:transcriptions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/transcriptions/{transcriptionId}": {
      "get": {
        "operationId": "get-session-transcription",
        "summary": "Get a session transcription by ID",
        "description": "Requires `read:transcriptions` scope (legacy tokens with empty scopes pass).",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "transcriptionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TranscriptionResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          },
          "404": {
            "description": "Not found"
          }
        }
      },
      "put": {
        "operationId": "update-transcription",
        "summary": "Update a transcription artifact",
        "description": "Requires `write:transcriptions` scope.",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "transcriptionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "additionalProperties": true
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TranscriptionResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing write:transcriptions scope"
          }
        }
      },
      "delete": {
        "operationId": "delete-transcription",
        "summary": "Delete a transcription artifact",
        "description": "Requires `write:transcriptions` scope.",
        "tags": [
          "Transcriptions"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "transcriptionId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Deleted"
          },
          "403": {
            "description": "Missing write:transcriptions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/recordings": {
      "get": {
        "operationId": "list-session-recordings",
        "summary": "List session audio recordings",
        "description": "Requires `read:transcriptions` scope (legacy tokens with empty scopes pass).",
        "tags": [
          "Session Recordings"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Recording"
                      }
                    }
                  }
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          }
        }
      },
      "post": {
        "operationId": "create-session-recording",
        "summary": "Initiate session audio upload",
        "description": "Returns a presigned upload URL for the audio file. Requires `write:transcriptions`.",
        "tags": [
          "Session Recordings"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "filename",
                  "size_bytes"
                ],
                "properties": {
                  "filename": {
                    "type": "string"
                  },
                  "content_type": {
                    "type": "string"
                  },
                  "size_bytes": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RecordingCreateResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing write:transcriptions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/recordings/{recordingId}": {
      "get": {
        "operationId": "get-session-recording",
        "summary": "Get a session audio recording",
        "description": "Requires `read:transcriptions` scope (legacy tokens with empty scopes pass).",
        "tags": [
          "Session Recordings"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "recordingId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RecordingResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:transcriptions scope"
          },
          "404": {
            "description": "Not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/recordings/{recordingId}/complete": {
      "post": {
        "operationId": "complete-session-recording",
        "summary": "Finalize session audio upload",
        "description": "Marks the recording as completed and normalizes common audio formats for playback.\nAlready-completed recordings return 200 without re-processing. Requires `write:transcriptions`.\n",
        "tags": [
          "Session Recordings"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "recordingId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "duration_seconds": {
                    "type": "number"
                  },
                  "file_size_bytes": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RecordingResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing write:transcriptions scope"
          },
          "422": {
            "description": "PCM transcode failed (TRANSCODE_ERROR)"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/media/upload/initiate": {
      "post": {
        "operationId": "initiate-media-upload",
        "summary": "Start multipart media upload",
        "description": "Begins a multipart upload for a video or audio file on a session. Requires `write:media`.",
        "tags": [
          "Media"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "filename",
                  "size_bytes"
                ],
                "properties": {
                  "filename": {
                    "type": "string"
                  },
                  "content_type": {
                    "type": "string"
                  },
                  "size_bytes": {
                    "type": "integer"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Created"
          },
          "403": {
            "description": "Missing write:media scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/media/upload/sign-part": {
      "post": {
        "operationId": "sign-media-upload-part",
        "summary": "Sign multipart upload parts",
        "description": "Requires `write:media`.",
        "tags": [
          "Media"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "key",
                  "upload_id",
                  "part_numbers"
                ],
                "properties": {
                  "key": {
                    "type": "string"
                  },
                  "upload_id": {
                    "type": "string"
                  },
                  "part_numbers": {
                    "type": "array",
                    "items": {
                      "type": "integer"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "403": {
            "description": "Missing write:media scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/media/upload/abort": {
      "post": {
        "operationId": "abort-media-upload",
        "summary": "Abort multipart upload",
        "description": "Requires `write:media`.",
        "tags": [
          "Media"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "key",
                  "upload_id"
                ],
                "properties": {
                  "key": {
                    "type": "string"
                  },
                  "upload_id": {
                    "type": "string"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "403": {
            "description": "Missing write:media scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/media/upload/complete": {
      "post": {
        "operationId": "complete-media-upload",
        "summary": "Complete multipart media upload",
        "description": "Finalizes the upload and starts automatic transcription. When you upload on a session URL,\ntranscript lines appear in the session transcription list when processing finishes.\nRequires `write:media`.\n",
        "tags": [
          "Media"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "key",
                  "upload_id",
                  "parts",
                  "filename",
                  "size_bytes"
                ],
                "properties": {
                  "key": {
                    "type": "string"
                  },
                  "upload_id": {
                    "type": "string"
                  },
                  "parts": {
                    "type": "array",
                    "items": {
                      "type": "object",
                      "required": [
                        "part_number",
                        "etag"
                      ],
                      "properties": {
                        "part_number": {
                          "type": "integer"
                        },
                        "etag": {
                          "type": "string"
                        }
                      }
                    }
                  },
                  "filename": {
                    "type": "string"
                  },
                  "size_bytes": {
                    "type": "integer"
                  },
                  "duration_seconds": {
                    "type": "number"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Created"
          },
          "403": {
            "description": "Missing write:media scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/media/{mediaItemId}": {
      "get": {
        "operationId": "get-media-item",
        "summary": "Get media item status",
        "description": "Check upload and transcription progress after completing an upload. Requires `read:media` (legacy tokens with empty scopes pass).",
        "tags": [
          "Media"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "mediaItemId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/MediaItemResponse"
                }
              }
            }
          },
          "403": {
            "description": "Missing read:media scope"
          },
          "404": {
            "description": "Not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/content-slots": {
      "get": {
        "operationId": "list-content-slots",
        "summary": "List upload slots",
        "description": "The files an event asks its speakers for — one slot per ask (Poster,\nPresentation, Handout, …), each with its own deadline, accepted file\ntypes and file count, in the order speakers see them. Configured by\norganizers under **Program → Settings → Files → Use upload slots**.\n\n`content_slot_id` on a [session file](/api-reference/session-files/list-files-attached-to-a-session)\npoints at one of these slots, so you can tell a poster from a deck without\nparsing filenames.\n\nRead-only. Active slots only unless `include_archived=true`. An event\nthat still uses a single file request for every session (the switch\nis off) returns an empty list. Requires `read:sessions` scope (legacy\ntokens with empty scopes pass).\n\nPass `session_id` to get only the slots that apply to one session\n(organizers can scope a slot to, say, poster-format sessions). That is\nthe list to pick a `content_slot_id` from before\n[creating a file](/api-reference/session-files/create-a-file-upload-for-a-session)\non that session.\n",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "name": "include_archived",
            "in": "query",
            "required": false,
            "schema": {
              "type": "boolean",
              "default": false
            },
            "description": "Also return archived slots (`is_active: false`). Ignored when `session_id` is set — an archived slot never applies to a session."
          },
          {
            "name": "session_id",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "Return only the active slots that apply to this session, in the\norder its speakers see them. `404` if the session is not on the\nevent.\n"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ContentSlotListResponse"
                },
                "examples": {
                  "two-slots": {
                    "summary": "A poster and a presentation ask",
                    "value": {
                      "data": [
                        {
                          "id": "2783cb27-958a-4a24-89d9-2d71387f04cc",
                          "name": "Poster",
                          "content_type": "poster",
                          "description": "Upload your poster as a single-page PDF.",
                          "due_date": null,
                          "due_date_extended": null,
                          "allowed_file_types": [
                            "pdf"
                          ],
                          "required": true,
                          "min_files": null,
                          "max_files": 1,
                          "allow_after_deadline": false,
                          "order": 0,
                          "is_active": true,
                          "created_at": "2026-10-02T12:04:11.000Z",
                          "updated_at": "2026-10-02T19:48:30.000Z"
                        },
                        {
                          "id": "9a1c6f0e-4a0b-4a4e-8e3f-0c2b1d5e7f90",
                          "name": "Presentation",
                          "content_type": "presentation",
                          "description": null,
                          "due_date": "2026-08-30T21:15:00.000Z",
                          "due_date_extended": null,
                          "allowed_file_types": [
                            "word",
                            "pdf"
                          ],
                          "required": false,
                          "min_files": null,
                          "max_files": 1,
                          "allow_after_deadline": false,
                          "order": 1,
                          "is_active": true,
                          "created_at": "2026-10-02T12:04:11.000Z",
                          "updated_at": "2026-10-02T12:04:11.000Z"
                        }
                      ]
                    }
                  },
                  "single-request": {
                    "summary": "Event still on a single file request",
                    "value": {
                      "data": []
                    }
                  }
                }
              }
            }
          },
          "403": {
            "description": "Missing read:sessions scope"
          },
          "404": {
            "description": "Event not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/files": {
      "get": {
        "operationId": "list-session-files",
        "summary": "List files attached to a session",
        "description": "Returns completed files on the session (latest version per file group).\nIncomplete uploads (create/replace without complete) are omitted.\nEach file carries `content_slot_id` — the [upload slot](/api-reference/session-files/list-upload-slots)\nit answers — once the event uses upload slots; `null` otherwise.\nRequires `read:sessions` scope (legacy tokens with empty scopes pass).\n",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "name": "type",
            "in": "query",
            "required": false,
            "description": "Only return files of these types. `type` is the organizer-facing\nfile type (`presentation`, `handout`, `poster`, `holding_slide`, …).\nPass one value, a comma-separated list, or repeat the parameter\n(`?type=holding_slide&type=handout`). Values are matched\ncase-insensitively; at most 20 values per request. A value with\ncharacters other than letters, digits, `_` and `-` answers `400`.\n",
            "schema": {
              "type": "string"
            },
            "examples": {
              "holdingSlide": {
                "summary": "Generated holding slides only",
                "value": "holding_slide"
              },
              "several": {
                "summary": "Several types",
                "value": "presentation,handout"
              }
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionFileListResponse"
                }
              }
            }
          },
          "400": {
            "description": "Malformed `type` filter"
          },
          "403": {
            "description": "Missing read:sessions scope"
          },
          "404": {
            "description": "Session not found"
          }
        }
      },
      "post": {
        "operationId": "create-session-file",
        "summary": "Initiate session file upload",
        "description": "Creates a file record and returns a short-lived S3 upload URL.\nRequires `write:sessions`.\n\nNext: `PUT` the file bytes to `data.upload.url`, then call\n`POST .../files/{fileId}/complete`. For files up to **50 MB**, prefer\n`POST .../files/upload` (one multipart call). This direct-to-storage\npath supports up to **500 MB**.\nSee [Uploading session files](/guides/uploading-session-files).\n",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/SessionFileCreateRequest"
              },
              "examples": {
                "powerpoint": {
                  "summary": "PowerPoint slides",
                  "value": {
                    "filename": "keynote-slides.pptx",
                    "size_bytes": 2457600,
                    "content_type": "application/vnd.openxmlformats-officedocument.presentationml.presentation",
                    "title": "Keynote slides"
                  }
                },
                "pdf": {
                  "summary": "PDF handout",
                  "value": {
                    "filename": "handout.pdf",
                    "size_bytes": 512000,
                    "content_type": "application/pdf",
                    "title": "Session handout"
                  }
                },
                "posterSlot": {
                  "summary": "Poster into the event's Poster slot",
                  "value": {
                    "filename": "poster.pdf",
                    "size_bytes": 3145728,
                    "content_type": "application/pdf",
                    "title": "Poster",
                    "content_slot_id": "2783cb27-958a-4a24-89d9-2d71387f04cc"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Created — upload URL included",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionFileCreateResponse"
                }
              }
            }
          },
          "400": {
            "description": "Validation error (missing fields, oversize, denied type, or a `content_slot_id` that is inactive, does not apply to the session, rejects the file type or is full)"
          },
          "403": {
            "description": "Missing write:sessions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/files/upload": {
      "post": {
        "operationId": "upload-session-file",
        "summary": "Upload a session file (simple)",
        "description": "Upload a file in one multipart request. Sessionboard detects size and\nMIME type from the bytes, runs security scanning, and returns the\nfinalized file. Max **50 MB**. Requires `write:sessions`.\n\nFor files larger than 50 MB (up to 500 MB), use the direct-to-storage\nflow: `POST .../files` → PUT to signed URL → `POST .../complete`.\nSee [Uploading session files](/guides/uploading-session-files).\n",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "required": [
                  "file"
                ],
                "properties": {
                  "file": {
                    "type": "string",
                    "format": "binary",
                    "description": "The file to attach (field name must be `file`)."
                  },
                  "title": {
                    "type": "string",
                    "description": "Display title. Defaults to the uploaded filename."
                  },
                  "assigned_participant_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Contact UUID of a session participant."
                  },
                  "content_slot_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Optional [upload slot](/api-reference/session-files/list-upload-slots)\nthis file answers. Same rules as `content_slot_id` on\n`POST .../files`: the slot must be active, apply to the\nsession, accept the file's type and have room; `400`\nnames the slot otherwise. Sets the file's `type`.\n"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Created — file attached and scanned",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionFileResponse"
                }
              }
            }
          },
          "400": {
            "description": "Validation error (missing file, oversize, denied type)"
          },
          "403": {
            "description": "Missing write:sessions scope"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/files/{fileId}/complete": {
      "post": {
        "operationId": "complete-session-file",
        "summary": "Finalize session file upload",
        "description": "Verifies the object in Sessionboard storage, runs security scanning\n(type deny-list + magic-byte checks; SVG sanitization when applicable),\nand finalizes the file on the session. Requires `write:sessions`.\n",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "$ref": "#/components/parameters/FileId"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionFileResponse"
                }
              }
            }
          },
          "400": {
            "description": "Upload missing, empty, or failed security checks"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "File not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/files/{fileId}/replace": {
      "post": {
        "operationId": "replace-session-file",
        "summary": "Replace session file bytes",
        "description": "Issues a new upload URL for the same file record. After `PUT`ing the new\nbytes, call `complete` again. Requires `write:sessions`. Max **500 MB**\n(direct-to-storage flow).\n",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "$ref": "#/components/parameters/FileId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/SessionFileCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK — new upload URL included",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionFileCreateResponse"
                }
              }
            }
          },
          "400": {
            "description": "Validation error"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "File not found"
          }
        }
      }
    },
    "/v1/event/{eventId}/sessions/{sessionId}/files/{fileId}": {
      "put": {
        "operationId": "update-session-file",
        "summary": "Update session file metadata",
        "description": "Updates display title and/or assigned participant. Does not change file\nbytes — use `replace` for that. Unknown fields are ignored.\nRequires `write:sessions`.\n",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "$ref": "#/components/parameters/FileId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/SessionFileUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SessionFileResponse"
                }
              }
            }
          },
          "400": {
            "description": "Validation error"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "File not found"
          }
        }
      },
      "delete": {
        "operationId": "delete-session-file",
        "summary": "Delete a session file",
        "description": "Soft-deletes the file from the session. Requires `write:sessions`.",
        "tags": [
          "Session Files"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/EventId"
          },
          {
            "$ref": "#/components/parameters/SessionId"
          },
          {
            "$ref": "#/components/parameters/FileId"
          }
        ],
        "responses": {
          "204": {
            "description": "No Content"
          },
          "403": {
            "description": "Missing write:sessions scope"
          },
          "404": {
            "description": "File not found"
          }
        }
      }
    },
    "/v1/logs/api-requests": {
      "get": {
        "operationId": "list-log-api-requests",
        "summary": "List API request logs",
        "description": "Every request made to this Public API, the MCP server and Insights with your\norganization's credentials, including requests rejected at authentication\n(`reason` carries `missing_token`, `invalid_token`, `revoked_token`,\n`expired_token`, `org_archived`, `member_inactive`, `ai_disabled`,\n`log_export_only` or `cross_org_event`). Kept for 365 days.\nRequest bodies are omitted unless you ask for them with `include=request_body`.\n",
        "tags": [
          "Log Export"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/LogCursor"
          },
          {
            "$ref": "#/components/parameters/LogSince"
          },
          {
            "$ref": "#/components/parameters/LogLimit"
          },
          {
            "name": "outcome",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "enum": [
                "success",
                "failure"
              ]
            },
            "description": "Only successful or only failed events."
          },
          {
            "name": "source",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "enum": [
                "public-api",
                "mcp",
                "insights"
              ]
            },
            "description": "Only requests that arrived through one surface."
          },
          {
            "name": "include",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "enum": [
                "request_body"
              ]
            },
            "description": "Add the logged request body to `details.request_body`."
          }
        ],
        "responses": {
          "200": {
            "description": "One page of events, oldest first.",
            "headers": {
              "RateLimit-Limit": {
                "$ref": "#/components/headers/RateLimitLimit"
              },
              "RateLimit-Remaining": {
                "$ref": "#/components/headers/RateLimitRemaining"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogPage"
                }
              }
            }
          },
          "400": {
            "description": "`VALIDATION_ERROR` for a bad parameter; `INVALID_CURSOR` for a cursor that is malformed or was issued for another stream or organization;\n`CURSOR_FILTER_MISMATCH` when the filters differ from the ones the cursor was issued with;\n`SINCE_BEFORE_RETENTION` when `since` is older than the stream keeps.\n",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogExportError"
                }
              }
            }
          },
          "401": {
            "description": "Missing, invalid, revoked or expired API token."
          },
          "403": {
            "description": "The token does not hold `read:audit_logs`, or it is an OAuth token. Log export accepts API tokens only."
          },
          "410": {
            "description": "`CURSOR_EXPIRED` — the cursor points before the start of retention. Restart from `since`.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogExportError"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited. 60 requests per minute per token; honor `Retry-After`."
          }
        }
      }
    },
    "/v1/logs/security-events": {
      "get": {
        "operationId": "list-log-security-events",
        "summary": "List security events",
        "description": "Sign-ins, sign-in failures, two-factor and passkey events, password resets and\nsession changes for the people in your organization. Covers events recorded\nagainst the organization and those of its current members.\nSessionboard staff activity is not included. No retention limit.\n",
        "tags": [
          "Log Export"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/LogCursor"
          },
          {
            "$ref": "#/components/parameters/LogSince"
          },
          {
            "$ref": "#/components/parameters/LogLimit"
          },
          {
            "name": "outcome",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "enum": [
                "success",
                "failure"
              ]
            },
            "description": "Only successful or only failed events."
          }
        ],
        "responses": {
          "200": {
            "description": "One page of events, oldest first.",
            "headers": {
              "RateLimit-Limit": {
                "$ref": "#/components/headers/RateLimitLimit"
              },
              "RateLimit-Remaining": {
                "$ref": "#/components/headers/RateLimitRemaining"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogPage"
                }
              }
            }
          },
          "400": {
            "description": "`VALIDATION_ERROR` for a bad parameter; `INVALID_CURSOR` for a cursor that is malformed or was issued for another stream or organization;\n`CURSOR_FILTER_MISMATCH` when the filters differ from the ones the cursor was issued with;\n`SINCE_BEFORE_RETENTION` when `since` is older than the stream keeps.\n",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogExportError"
                }
              }
            }
          },
          "401": {
            "description": "Missing, invalid, revoked or expired API token."
          },
          "403": {
            "description": "The token does not hold `read:audit_logs`, or it is an OAuth token. Log export accepts API tokens only."
          },
          "410": {
            "description": "`CURSOR_EXPIRED` — the cursor points before the start of retention. Restart from `since`.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogExportError"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited. 60 requests per minute per token; honor `Retry-After`."
          }
        }
      }
    },
    "/v1/logs/audit-trail": {
      "get": {
        "operationId": "list-log-audit-trail",
        "summary": "List audit trail",
        "description": "Every recorded change to your organization's data — who changed which record,\nwhich property, and (by default) the new value. `action` is\n`<subject_type>.<operation>`, for example `session.update`. No retention limit.\n",
        "tags": [
          "Log Export"
        ],
        "security": [
          {
            "ApiKey": []
          }
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/LogCursor"
          },
          {
            "$ref": "#/components/parameters/LogSince"
          },
          {
            "$ref": "#/components/parameters/LogLimit"
          },
          {
            "name": "subject_type",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "example": "session,contact"
            },
            "description": "Comma-separated record types to include, for example `session,contact`."
          },
          {
            "name": "include_values",
            "in": "query",
            "required": false,
            "schema": {
              "type": "boolean",
              "default": true
            },
            "description": "Set `false` to omit changed values (`details.value`) — useful when the SIEM must not hold personal data."
          }
        ],
        "responses": {
          "200": {
            "description": "One page of events, oldest first.",
            "headers": {
              "RateLimit-Limit": {
                "$ref": "#/components/headers/RateLimitLimit"
              },
              "RateLimit-Remaining": {
                "$ref": "#/components/headers/RateLimitRemaining"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogPage"
                }
              }
            }
          },
          "400": {
            "description": "`VALIDATION_ERROR` for a bad parameter; `INVALID_CURSOR` for a cursor that is malformed or was issued for another stream or organization;\n`CURSOR_FILTER_MISMATCH` when the filters differ from the ones the cursor was issued with;\n`SINCE_BEFORE_RETENTION` when `since` is older than the stream keeps.\n",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogExportError"
                }
              }
            }
          },
          "401": {
            "description": "Missing, invalid, revoked or expired API token."
          },
          "403": {
            "description": "The token does not hold `read:audit_logs`, or it is an OAuth token. Log export accepts API tokens only."
          },
          "410": {
            "description": "`CURSOR_EXPIRED` — the cursor points before the start of retention. Restart from `since`.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/LogExportError"
                }
              }
            }
          },
          "429": {
            "description": "Rate limited. 60 requests per minute per token; honor `Retry-After`."
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs": {
      "get": {
        "operationId": "list-awards-programs",
        "summary": "List programs",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/AwardsPageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/AwardsProgram"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/create": {
      "post": {
        "operationId": "create-awards-program",
        "summary": "Create a program",
        "description": "Creates the program with its submission form, a default round, and the token owner as program manager — the same as creating it in the admin app. Counts against the plan's Awards program limit. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "allOf": [
                  {
                    "$ref": "#/components/schemas/AwardsProgramWrite"
                  }
                ],
                "required": [
                  "name"
                ]
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Program created",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsProgram"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Your plan allows 3 Awards programs (403 also means the token lacks `write:awards`)",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "FORBIDDEN",
                  "message": "Your plan allows 3 Awards programs (403 also means the token lacks `write:awards`)"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}": {
      "get": {
        "operationId": "get-awards-program",
        "summary": "Get a program",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsProgram"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        },
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          }
        ]
      },
      "put": {
        "operationId": "update-awards-program",
        "summary": "Update a program",
        "description": "Fields you omit keep their stored value. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsProgramWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Program updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsProgram"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "patch": {
        "operationId": "patch-awards-program",
        "summary": "Update a program (PATCH)",
        "description": "Fields you omit keep their stored value. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsProgramWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Program updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsProgram"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "delete": {
        "operationId": "delete-awards-program",
        "summary": "Delete a program",
        "description": "Soft-deletes the program (it moves to Trash and can be restored in the admin app). A program that has submissions returns `409` unless `force=true` is sent — the API equivalent of the admin app's confirmation dialog. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsForce"
          }
        ],
        "responses": {
          "204": {
            "description": "Program deleted"
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          },
          "409": {
            "description": "Program has 12 submissions; send force=true to delete it",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "CONFLICT",
                  "message": "Program has 12 submissions; send force=true to delete it"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/categories": {
      "get": {
        "operationId": "list-awards-categorys",
        "summary": "List categorys",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/AwardsPageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/AwardsCategory"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/categories/create": {
      "post": {
        "operationId": "create-awards-category",
        "summary": "Create a category",
        "description": "Set `parent_category_id` to another category in the same program to create a subcategory. `order` defaults to the end of the list. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "allOf": [
                  {
                    "$ref": "#/components/schemas/AwardsCategoryWrite"
                  }
                ],
                "required": [
                  "name"
                ]
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Category created",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsCategory"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/categories/{categoryId}": {
      "get": {
        "operationId": "get-awards-category",
        "summary": "Get a category",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsCategory"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        },
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "categoryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The category ID."
          }
        ]
      },
      "put": {
        "operationId": "update-awards-category",
        "summary": "Update a category",
        "description": "A parent in another program, the category itself, or one of its own subcategories returns `400`. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "categoryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The category ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsCategoryWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Category updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsCategory"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "patch": {
        "operationId": "patch-awards-category",
        "summary": "Update a category (PATCH)",
        "description": "A parent in another program, the category itself, or one of its own subcategories returns `400`. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "categoryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The category ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsCategoryWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Category updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsCategory"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "delete": {
        "operationId": "delete-awards-category",
        "summary": "Delete a category",
        "description": "Soft-deletes the category. One with subcategories returns `409` unless `cascade=true` is sent, which deletes the whole subtree. One that submissions are filed under (directly or through a subcategory) also returns `409` unless `force=true` is sent. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "categoryId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The category ID."
          },
          {
            "$ref": "#/components/parameters/AwardsCascade"
          },
          {
            "$ref": "#/components/parameters/AwardsForce"
          }
        ],
        "responses": {
          "204": {
            "description": "Category deleted"
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          },
          "409": {
            "description": "Category has 2 subcategories; send cascade=true to delete them too",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "CONFLICT",
                  "message": "Category has 2 subcategories; send cascade=true to delete them too"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/rounds": {
      "get": {
        "operationId": "list-awards-rounds",
        "summary": "List rounds",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/AwardsPageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/AwardsRound"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/rounds/create": {
      "post": {
        "operationId": "create-awards-round",
        "summary": "Create a round",
        "description": "Adds a review round to the program. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "allOf": [
                  {
                    "$ref": "#/components/schemas/AwardsRoundWrite"
                  }
                ],
                "required": [
                  "name"
                ]
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Round created",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsRound"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/rounds/{roundId}": {
      "get": {
        "operationId": "get-awards-round",
        "summary": "Get a round",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsRound"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        },
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "roundId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The round ID."
          }
        ]
      },
      "put": {
        "operationId": "update-awards-round",
        "summary": "Update a round",
        "description": "Fields you omit keep their stored value. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "roundId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The round ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsRoundWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Round updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsRound"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "patch": {
        "operationId": "patch-awards-round",
        "summary": "Update a round (PATCH)",
        "description": "Fields you omit keep their stored value. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "roundId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The round ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsRoundWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Round updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsRound"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "delete": {
        "operationId": "delete-awards-round",
        "summary": "Delete a round",
        "description": "Soft-deletes the round and moves its submissions back to the previous round, as the admin app does. The program's default (first) round cannot be deleted and returns `422`. A round with reviewer assignments returns `409` unless `force=true` is sent. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "roundId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The round ID."
          },
          {
            "$ref": "#/components/parameters/AwardsForce"
          }
        ],
        "responses": {
          "204": {
            "description": "Round deleted"
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          },
          "409": {
            "description": "Round has 8 reviewer assignments; send force=true to delete it",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "CONFLICT",
                  "message": "Round has 8 reviewer assignments; send force=true to delete it"
                }
              }
            }
          },
          "422": {
            "description": "The default round cannot be deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "The default round cannot be deleted"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/promo-codes": {
      "get": {
        "operationId": "list-awards-promo-codes",
        "summary": "List promo codes",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/AwardsPageSize"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/AwardsPromoCode"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/promo-codes/create": {
      "post": {
        "operationId": "create-awards-promo-code",
        "summary": "Create a promo code",
        "description": "Codes are stored upper-case and must be unique within the program. A `percentage` amount above 100 returns `400`; `percentage` 100 waives the fee entirely. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "allOf": [
                  {
                    "$ref": "#/components/schemas/AwardsPromoCodeWrite"
                  }
                ],
                "required": [
                  "code",
                  "type",
                  "amount"
                ]
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Promo code created",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsPromoCode"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          },
          "409": {
            "description": "Promo code SAVE20 already exists in this program",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "CONFLICT",
                  "message": "Promo code SAVE20 already exists in this program"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/promo-codes/{promoCodeId}": {
      "get": {
        "operationId": "get-awards-promo-code",
        "summary": "Get a promo code",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsPromoCode"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        },
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "promoCodeId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The promo code ID."
          }
        ]
      },
      "put": {
        "operationId": "update-awards-promo-code",
        "summary": "Update a promo code",
        "description": "Renaming to a code already used in the program returns `409`. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "promoCodeId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The promo code ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsPromoCodeWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Promo code updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsPromoCode"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          },
          "409": {
            "description": "Promo code SAVE20 already exists in this program",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "CONFLICT",
                  "message": "Promo code SAVE20 already exists in this program"
                }
              }
            }
          }
        }
      },
      "patch": {
        "operationId": "patch-awards-promo-code",
        "summary": "Update a promo code (PATCH)",
        "description": "Renaming to a code already used in the program returns `409`. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "promoCodeId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The promo code ID."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsPromoCodeWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Promo code updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsPromoCode"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          },
          "409": {
            "description": "Promo code SAVE20 already exists in this program",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "CONFLICT",
                  "message": "Promo code SAVE20 already exists in this program"
                }
              }
            }
          }
        }
      },
      "delete": {
        "operationId": "delete-awards-promo-code",
        "summary": "Delete a promo code",
        "description": "Soft-deletes the code. A code already applied to a submission returns `409` unless `force=true` is sent; those submissions keep their discount. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "name": "promoCodeId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The promo code ID."
          },
          {
            "$ref": "#/components/parameters/AwardsForce"
          }
        ],
        "responses": {
          "204": {
            "description": "Promo code deleted"
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          },
          "409": {
            "description": "Promo code has been redeemed 3 times; send force=true to delete it",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "CONFLICT",
                  "message": "Promo code has been redeemed 3 times; send force=true to delete it"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/submissions": {
      "get": {
        "operationId": "list-awards-submissions",
        "summary": "List submissions",
        "description": "Lists top-level submissions (merged duplicates are folded into their primary). Submissions are created by submitters through the program's portal, not through the API. Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/Page"
          },
          {
            "$ref": "#/components/parameters/AwardsPageSize"
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Only submissions in this status, e.g. `submitted`."
          },
          {
            "name": "category_id",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "current_round_id",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/AwardsSubmission"
                      }
                    },
                    "pagination": {
                      "$ref": "#/components/schemas/ListPagination"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/submissions/{submissionId}": {
      "get": {
        "operationId": "get-awards-submission",
        "summary": "Get a submission",
        "description": "Includes `values`, the form answers keyed by form field ID. Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsSubmission"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        },
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsSubmissionId"
          }
        ]
      },
      "put": {
        "operationId": "update-awards-submission",
        "summary": "Update a submission",
        "description": "Writes answers to the submission form, keyed by form field ID, with the same required-field checks and edit history as an admin edit. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsSubmissionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsSubmissionWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Submission updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsSubmission"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "patch": {
        "operationId": "patch-awards-submission",
        "summary": "Update a submission (PATCH)",
        "description": "Writes answers to the submission form, keyed by form field ID, with the same required-field checks and edit history as an admin edit. `PUT` and `PATCH` behave the same: send only the fields you are changing. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsSubmissionId"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AwardsSubmissionWrite"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Submission updated",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsSubmission"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid body or id",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "VALIDATION_ERROR",
                  "message": "\"name\" is not allowed to be empty"
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "delete": {
        "operationId": "delete-awards-submission",
        "summary": "Delete a submission",
        "description": "Soft-deletes the submission (it moves to Trash and can be restored in the admin app). Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsSubmissionId"
          }
        ],
        "responses": {
          "204": {
            "description": "Submission deleted"
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/submissions/{submissionId}/reviews": {
      "get": {
        "operationId": "list-awards-reviews",
        "summary": "List reviews",
        "description": "One entry per reviewer assigned to the submission, with their scores. Reviews are written by reviewers in the review portal, not through the API. Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsSubmissionId"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/AwardsReview"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    },
    "/v1/organization/{orgId}/awards/programs/{programId}/submissions/{submissionId}/reviews/{reviewId}": {
      "get": {
        "operationId": "get-awards-review",
        "summary": "Get a review",
        "description": "Requires the `read:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsSubmissionId"
          },
          {
            "name": "reviewId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The review (reviewer assignment) ID."
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "data": {
                      "$ref": "#/components/schemas/AwardsReview"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `read:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: read:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      },
      "delete": {
        "operationId": "delete-awards-review",
        "summary": "Remove a review",
        "description": "Unassigns the reviewer from the submission for that round and removes their scores, as unassigning in the admin app does. Requires the `write:awards` scope.",
        "tags": [
          "Awards"
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/AwardsOrgId"
          },
          {
            "$ref": "#/components/parameters/AwardsProgramId"
          },
          {
            "$ref": "#/components/parameters/AwardsSubmissionId"
          },
          {
            "name": "reviewId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "The review (reviewer assignment) ID."
          }
        ],
        "responses": {
          "204": {
            "description": "Review removed"
          },
          "401": {
            "description": "Missing or invalid token"
          },
          "403": {
            "description": "Token lacks `write:awards`",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "SCOPE_REQUIRED",
                  "message": "Token missing required scope: write:awards"
                }
              }
            }
          },
          "404": {
            "description": "Not found — also returned for any id belonging to another organization",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AwardsError"
                },
                "example": {
                  "error": "NOT_FOUND",
                  "message": "Not found"
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "ApiKey": {
        "type": "apiKey",
        "in": "header",
        "name": "x-access-token",
        "description": "Organization API token. Generate from Organization Settings → API Tokens."
      },
      "BearerToken": {
        "type": "http",
        "scheme": "bearer",
        "description": "OAuth 2.1 access token. Obtained via the OAuth PKCE flow at `/oauth/token`."
      }
    },
    "headers": {
      "RateLimitLimit": {
        "description": "Requests allowed in the current window.",
        "schema": {
          "type": "integer"
        }
      },
      "RateLimitRemaining": {
        "description": "Requests left in the current window.",
        "schema": {
          "type": "integer"
        }
      }
    },
    "parameters": {
      "AwardsOrgId": {
        "name": "orgId",
        "in": "path",
        "required": true,
        "schema": {
          "type": "string"
        },
        "description": "Your organization ID. Any other organization returns `404`."
      },
      "AwardsProgramId": {
        "name": "programId",
        "in": "path",
        "required": true,
        "schema": {
          "type": "string",
          "format": "uuid"
        },
        "description": "The Awards program ID."
      },
      "AwardsSubmissionId": {
        "name": "submissionId",
        "in": "path",
        "required": true,
        "schema": {
          "type": "string",
          "format": "uuid"
        },
        "description": "The submission ID."
      },
      "AwardsPageSize": {
        "name": "pageSize",
        "in": "query",
        "required": false,
        "schema": {
          "type": "integer",
          "minimum": 1,
          "maximum": 100,
          "default": 25
        },
        "description": "Results per page. `page_size` is also accepted."
      },
      "AwardsForce": {
        "name": "force",
        "in": "query",
        "required": false,
        "schema": {
          "type": "boolean",
          "default": false
        },
        "description": "Delete even though the record is in use (see the `409` response)."
      },
      "AwardsCascade": {
        "name": "cascade",
        "in": "query",
        "required": false,
        "schema": {
          "type": "boolean",
          "default": false
        },
        "description": "Also delete the category's subcategories."
      },
      "LogCursor": {
        "name": "cursor",
        "in": "query",
        "required": false,
        "schema": {
          "type": "string",
          "maxLength": 2048
        },
        "description": "`next_cursor` from the previous page. Store it after each page and send it back unchanged;\nit remembers your filters, so repeat the same filters with it.\n"
      },
      "LogSince": {
        "name": "since",
        "in": "query",
        "required": false,
        "schema": {
          "type": "string",
          "format": "date-time"
        },
        "description": "Where to start when you have no cursor. Defaults to 24 hours ago. Ignored when `cursor` is sent."
      },
      "LogLimit": {
        "name": "limit",
        "in": "query",
        "required": false,
        "schema": {
          "type": "integer",
          "minimum": 1,
          "maximum": 1000,
          "default": 500
        },
        "description": "Events per page."
      },
      "EventId": {
        "name": "eventId",
        "in": "path",
        "required": true,
        "schema": {
          "type": "integer"
        },
        "description": "Event ID"
      },
      "SessionId": {
        "name": "sessionId",
        "in": "path",
        "required": true,
        "schema": {
          "type": "string",
          "format": "uuid"
        },
        "description": "Session UUID"
      },
      "FileId": {
        "name": "fileId",
        "in": "path",
        "required": true,
        "schema": {
          "type": "string",
          "format": "uuid"
        },
        "description": "Session file (Content) UUID"
      },
      "Page": {
        "name": "page",
        "in": "query",
        "required": false,
        "schema": {
          "type": "integer",
          "minimum": 1,
          "maximum": 999,
          "default": 1
        },
        "description": "Page number for pagination."
      },
      "PageSize": {
        "name": "pageSize",
        "in": "query",
        "required": false,
        "schema": {
          "type": "integer",
          "minimum": 1,
          "maximum": 100,
          "default": 25
        },
        "description": "Number of results per page.\n\nThe event-settings list endpoints (tags, tracks, levels, formats,\nrooms, languages, statuses) also accept the older spelling\n`page_size`, and used to accept only that — a request sending\n`pageSize` silently got the default 25. Both now work, `pageSize`\nwins when both are sent, and on these endpoints a value outside\n1–100 is clamped rather than rejected. Everywhere else `pageSize`\nis the only spelling.\n"
      },
      "Expand": {
        "name": "expand",
        "in": "query",
        "required": false,
        "schema": {
          "type": "array",
          "items": {
            "type": "string",
            "enum": [
              "translated_fields",
              "subsession_details",
              "linked_sources",
              "composition"
            ]
          }
        },
        "description": "Expand records with additional data.\n\nPossible values:\n- `translated_fields` — includes the `translated_fields` array on records when the event has language variants configured.\n- `subsession_details` — applies to session responses. Each subsession inside `parent.subsessions[]` is returned with full parent-session field parity (`status`, `custom_status`, `custom_fields`, `chairpersons`, `moderators`, `sponsors`, `exhibitors`, `tags`, `language`, `track`, `level`, `room`, `is_public`, `external_url`, `client_session_id`, `ceu_credits`, `capacity`, `source`) instead of the default minimal shape. Subsessions inherit `is_abstract`, `composition_status`, and optional `composition` from the parent. Not required when calling `GET /v1/event/{eventId}/sessions/{sessionId}` with a subsession UUID — that endpoint always returns the full shape at the top level.\n- `linked_sources` — include sessions that are linked as composition sources (excluded from list/search results by default).\n- `composition` — attach a full `composition` object with target and source details on each returned session. Recommended for single-session GET; use cautiously on broad searches.\n\nA single value can be passed directly, and multiple values repeat\nthe parameter — all of these are accepted:\n- `?expand=composition`\n- `?expand=translated_fields&expand=composition`\n- `?expand[]=translated_fields&expand[]=composition`\n"
      },
      "ListEventsExpand": {
        "name": "expand",
        "in": "query",
        "required": false,
        "style": "form",
        "explode": true,
        "schema": {
          "type": "array",
          "items": {
            "type": "string",
            "enum": [
              "custom_fields",
              "integration_mappings"
            ]
          }
        },
        "description": "Extra collections on each event in `GET /v1/events`. Not the same enum\nas session `Expand` (`translated_fields`, `composition`, …).\n\nRepeat the parameter (`?expand=custom_fields&expand=integration_mappings`)\nor comma-separate (`?expand=custom_fields,integration_mappings`).\n\n- `custom_fields` — org-defined Event custom field values. Omitted from\n  the payload when this expand is not requested. Present as `[]` when\n  requested and the event has no values.\n- `integration_mappings` — `{ name, source, external_event_id }` rows\n  from conference `Integration_*_Event_Mappings` (via the union view).\n  `source` uses underscores (`expo_platform`, not `expo-platform`).\n  LiveBuzz / apps-engine campaign IDs are not included.\n"
      }
    },
    "schemas": {
      "AwardsError": {
        "type": "object",
        "properties": {
          "error": {
            "type": "string",
            "enum": [
              "VALIDATION_ERROR",
              "SCOPE_REQUIRED",
              "FORBIDDEN",
              "NOT_FOUND",
              "CONFLICT"
            ]
          },
          "message": {
            "type": "string"
          }
        }
      },
      "AwardsProgram": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "org_id": {
            "type": "string"
          },
          "name": {
            "type": "string",
            "examples": [
              "2027 Excellence Awards"
            ]
          },
          "slug": {
            "type": "string",
            "examples": [
              "2027-excellence-awards"
            ]
          },
          "nomenclature": {
            "type": "string",
            "enum": [
              "awards",
              "grants",
              "scholarships"
            ]
          },
          "description": {
            "type": [
              "string",
              "null"
            ]
          },
          "status": {
            "type": "string",
            "enum": [
              "draft",
              "open",
              "reviewing",
              "closed",
              "archived"
            ]
          },
          "year": {
            "type": [
              "integer",
              "null"
            ]
          },
          "deadline": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "collects_fees": {
            "type": "boolean"
          },
          "pricing_type": {
            "type": [
              "string",
              "null"
            ]
          },
          "base_fee": {
            "type": [
              "number",
              "null"
            ]
          },
          "submitter_editing_policy": {
            "type": "string",
            "enum": [
              "never",
              "while_open",
              "while_open_after_payment"
            ]
          },
          "notify_on_submitter_edit": {
            "type": "boolean"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "AwardsProgramWrite": {
        "type": "object",
        "additionalProperties": false,
        "properties": {
          "name": {
            "type": "string",
            "minLength": 1,
            "maxLength": 255
          },
          "nomenclature": {
            "type": "string",
            "enum": [
              "awards",
              "grants",
              "scholarships"
            ]
          },
          "description": {
            "type": [
              "string",
              "null"
            ]
          },
          "slug": {
            "type": "string",
            "minLength": 1,
            "maxLength": 255,
            "description": "Defaults to one derived from `name` on create."
          },
          "status": {
            "type": "string",
            "enum": [
              "draft",
              "open",
              "reviewing",
              "closed",
              "archived"
            ],
            "description": "Update only."
          },
          "year": {
            "type": [
              "integer",
              "null"
            ]
          },
          "deadline": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "collects_fees": {
            "type": "boolean",
            "description": "Update only."
          },
          "submitter_editing_policy": {
            "type": "string",
            "enum": [
              "never",
              "while_open",
              "while_open_after_payment"
            ]
          },
          "notify_on_submitter_edit": {
            "type": "boolean"
          },
          "default_submission_status": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "submitted",
              "under_review",
              "accepted",
              "rejected",
              "",
              null
            ],
            "description": "Status a new submission starts in. Empty string or `null` clears it."
          }
        }
      },
      "AwardsCategory": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "program_id": {
            "type": "string",
            "format": "uuid"
          },
          "name": {
            "type": "string",
            "examples": [
              "Best Innovation"
            ]
          },
          "description": {
            "type": [
              "string",
              "null"
            ]
          },
          "parent_category_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid"
          },
          "submission_limit": {
            "type": [
              "integer",
              "null"
            ]
          },
          "expertise_tags": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "order": {
            "type": "integer"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "AwardsCategoryWrite": {
        "type": "object",
        "additionalProperties": false,
        "properties": {
          "name": {
            "type": "string",
            "minLength": 1,
            "maxLength": 255
          },
          "description": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 10000
          },
          "parent_category_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid",
            "description": "Another category in the same program. `null` makes it top-level."
          },
          "submission_limit": {
            "type": [
              "integer",
              "null"
            ],
            "minimum": 0,
            "description": "Most submissions one submitter may file in this category."
          },
          "expertise_tags": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "order": {
            "type": "integer"
          }
        }
      },
      "AwardsRound": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "program_id": {
            "type": "string",
            "format": "uuid"
          },
          "name": {
            "type": "string",
            "examples": [
              "Final judging"
            ]
          },
          "round_type": {
            "type": "string",
            "enum": [
              "submission_review",
              "review_only"
            ]
          },
          "is_default": {
            "type": "boolean",
            "description": "The program's first round. It cannot be deleted."
          },
          "submission_start_date": {
            "type": [
              "string",
              "null"
            ]
          },
          "submission_end_date": {
            "type": [
              "string",
              "null"
            ]
          },
          "review_start_date": {
            "type": [
              "string",
              "null"
            ]
          },
          "review_end_date": {
            "type": [
              "string",
              "null"
            ]
          },
          "passing_score": {
            "type": [
              "number",
              "null"
            ]
          },
          "blind_review": {
            "type": "boolean"
          },
          "instructions": {
            "type": [
              "string",
              "null"
            ]
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "AwardsRoundWrite": {
        "type": "object",
        "additionalProperties": false,
        "properties": {
          "name": {
            "type": "string",
            "minLength": 1,
            "maxLength": 255
          },
          "round_type": {
            "type": "string",
            "enum": [
              "submission_review",
              "review_only"
            ]
          },
          "submission_start_date": {
            "type": [
              "string",
              "null"
            ],
            "description": "`YYYY-MM-DD` or an ISO 8601 timestamp."
          },
          "submission_end_date": {
            "type": [
              "string",
              "null"
            ],
            "description": "`YYYY-MM-DD` or an ISO 8601 timestamp."
          },
          "review_start_date": {
            "type": [
              "string",
              "null"
            ],
            "description": "`YYYY-MM-DD` or an ISO 8601 timestamp."
          },
          "review_end_date": {
            "type": [
              "string",
              "null"
            ],
            "description": "`YYYY-MM-DD` or an ISO 8601 timestamp."
          },
          "passing_score": {
            "type": [
              "number",
              "null"
            ]
          },
          "blind_review": {
            "type": "boolean",
            "description": "Hide submitter identity from reviewers."
          },
          "instructions": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 20000
          }
        }
      },
      "AwardsPromoCode": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "program_id": {
            "type": "string",
            "format": "uuid"
          },
          "code": {
            "type": "string",
            "examples": [
              "SAVE20"
            ]
          },
          "type": {
            "type": "string",
            "enum": [
              "percentage",
              "flat"
            ]
          },
          "amount": {
            "type": "number",
            "examples": [
              20
            ]
          },
          "starts_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "ends_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "redemption_count": {
            "type": "integer",
            "description": "Submissions the code has been applied to. Returned by the single-code GET only."
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "AwardsPromoCodeWrite": {
        "type": "object",
        "additionalProperties": false,
        "properties": {
          "code": {
            "type": "string",
            "maxLength": 255,
            "pattern": "^[A-Za-z0-9]+$",
            "description": "Letters and digits; stored upper-case."
          },
          "type": {
            "type": "string",
            "enum": [
              "percentage",
              "flat"
            ]
          },
          "amount": {
            "type": "number",
            "minimum": 0,
            "description": "Percent off (at most 100) or a flat amount in the program's currency."
          },
          "starts_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "ends_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          }
        }
      },
      "AwardsSubmission": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "program_id": {
            "type": "string",
            "format": "uuid"
          },
          "category_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string",
            "examples": [
              "AWD-0042"
            ]
          },
          "status": {
            "type": "string",
            "examples": [
              "submitted"
            ]
          },
          "current_round_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid"
          },
          "payment_status": {
            "type": [
              "string",
              "null"
            ]
          },
          "promo_code_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid"
          },
          "submitted_by_user_id": {
            "type": [
              "integer",
              "null"
            ]
          },
          "submitted_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "total_score": {
            "type": [
              "number",
              "null"
            ]
          },
          "merged_into_submission_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid"
          },
          "values": {
            "type": "object",
            "additionalProperties": true,
            "description": "Form answers keyed by form field ID. Returned by the single-submission GET and by updates."
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "AwardsSubmissionWrite": {
        "type": "object",
        "additionalProperties": false,
        "properties": {
          "values": {
            "type": "object",
            "additionalProperties": true,
            "description": "Answers keyed by form field ID. Fields you omit are left unchanged; a required field sent empty returns `400`."
          },
          "allow_submitter_editing_override": {
            "type": [
              "boolean",
              "null"
            ],
            "description": "Let this submitter edit regardless of the program's editing policy. `null` clears the override."
          }
        }
      },
      "AwardsReview": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "submission_id": {
            "type": "string",
            "format": "uuid"
          },
          "round_id": {
            "type": "string",
            "format": "uuid"
          },
          "reviewer_user_id": {
            "type": "integer"
          },
          "is_abstained": {
            "type": "boolean"
          },
          "abstain_reason": {
            "type": [
              "string",
              "null"
            ]
          },
          "scores": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "field_id": {
                  "type": "string",
                  "format": "uuid"
                },
                "value": {
                  "description": "Number, text, or JSON depending on the scorecard field."
                }
              }
            }
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "LogPage": {
        "type": "object",
        "required": [
          "data",
          "next_cursor",
          "has_more"
        ],
        "properties": {
          "data": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/LogEvent"
            }
          },
          "next_cursor": {
            "type": "string",
            "description": "Send this as `cursor` on the next call. On an empty page it is the cursor you sent,\nso a caught-up poller keeps it and waits.\n"
          },
          "has_more": {
            "type": "boolean",
            "description": "`true` when more events are ready now — fetch again immediately. `false` means wait before polling."
          }
        }
      },
      "LogEvent": {
        "type": "object",
        "description": "One event, in the same shape on every stream. Events appear about a minute after they happen\nand are ordered by when Sessionboard recorded them, so a late-arriving event is never skipped.\n",
        "properties": {
          "id": {
            "type": "string",
            "description": "Stable event id. Use it to de-duplicate if you replay a page."
          },
          "stream": {
            "type": "string",
            "enum": [
              "api_request",
              "security_event",
              "audit"
            ],
            "description": "Which log the event came from — `api_request` from `/v1/logs/api-requests`, `security_event` from `/v1/logs/security-events`, `audit` from `/v1/logs/audit-trail`."
          },
          "occurred_at": {
            "type": "string",
            "format": "date-time",
            "description": "When the event happened."
          },
          "ingested_at": {
            "type": "string",
            "format": "date-time",
            "description": "When Sessionboard recorded it. Pages are ordered by this."
          },
          "action": {
            "type": "string",
            "description": "`GET /v1/events` for API requests, the event type (for example `login.password_ok` or `login.challenge_failed`) for security events, `<subject_type>.<operation>` for the audit trail.",
            "example": "GET /v1/events"
          },
          "outcome": {
            "type": "string",
            "enum": [
              "success",
              "failure",
              "unknown"
            ]
          },
          "reason": {
            "type": "string",
            "nullable": true,
            "description": "Why it failed, when it did."
          },
          "actor": {
            "type": "object",
            "properties": {
              "type": {
                "type": "string",
                "description": "`api_token`, `oauth_token` or `anonymous` for API requests; `user` or `admin` for security events; `user`, `system` or `rule` (an automation) for the audit trail."
              },
              "id": {
                "type": "string",
                "nullable": true
              },
              "name": {
                "type": "string",
                "nullable": true
              },
              "token_hint": {
                "type": "string",
                "nullable": true,
                "description": "Last characters of the token id, for API requests."
              },
              "user_email": {
                "type": "string",
                "nullable": true
              }
            }
          },
          "src_ip": {
            "type": "string",
            "nullable": true
          },
          "user_agent": {
            "type": "string",
            "nullable": true
          },
          "status": {
            "type": "integer",
            "nullable": true,
            "description": "HTTP status, for API requests."
          },
          "duration_ms": {
            "type": "integer",
            "nullable": true,
            "description": "Response time, for API requests."
          },
          "target": {
            "type": "object",
            "nullable": true,
            "properties": {
              "type": {
                "type": "string",
                "example": "event"
              },
              "id": {
                "type": "string"
              }
            }
          },
          "details": {
            "type": "object",
            "additionalProperties": true,
            "description": "Stream-specific fields (for example `source` and `request_id` for API requests, `property` and `value` for the audit trail)."
          }
        }
      },
      "LogExportError": {
        "type": "object",
        "properties": {
          "error": {
            "type": "string",
            "enum": [
              "VALIDATION_ERROR",
              "INVALID_CURSOR",
              "CURSOR_FILTER_MISMATCH",
              "SINCE_BEFORE_RETENTION",
              "CURSOR_EXPIRED"
            ]
          },
          "message": {
            "type": "string"
          }
        }
      },
      "DateRangeFilter": {
        "type": "object",
        "description": "Filter by a date range using before and/or after bounds.",
        "properties": {
          "before": {
            "type": "string",
            "format": "date-time",
            "description": "Return records before this date-time."
          },
          "after": {
            "type": "string",
            "format": "date-time",
            "description": "Return records after this date-time."
          }
        }
      },
      "NestedSortField": {
        "type": "object",
        "description": "One sort key. `sort` is the direction; `order` is the priority when\nmultiple keys are set (lower numbers apply first).\n",
        "properties": {
          "sort": {
            "type": "string",
            "enum": [
              "asc",
              "desc"
            ]
          },
          "order": {
            "type": "integer"
          }
        }
      },
      "SortOptions": {
        "type": "object",
        "description": "Nested sort keys matching the search POST body (`createdAt.sort`, not a\nflat `order` enum). Each key is optional.\n",
        "properties": {
          "createdAt": {
            "$ref": "#/components/schemas/NestedSortField"
          },
          "updatedAt": {
            "$ref": "#/components/schemas/NestedSortField"
          }
        }
      },
      "SessionSortOptions": {
        "type": "object",
        "description": "Session search sort. Same nested shape as `SortOptions`, plus `startsAt`.",
        "properties": {
          "createdAt": {
            "$ref": "#/components/schemas/NestedSortField"
          },
          "updatedAt": {
            "$ref": "#/components/schemas/NestedSortField"
          },
          "startsAt": {
            "allOf": [
              {
                "$ref": "#/components/schemas/NestedSortField"
              }
            ],
            "description": "Sort by session start time. Null `starts_at` values always sort last.\n"
          }
        }
      },
      "RecordSearchBody": {
        "type": "object",
        "description": "Common search request body used across multiple endpoints.",
        "properties": {
          "filters": {
            "type": "object",
            "properties": {
              "createdAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "updatedAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "status": {
                "type": "string",
                "enum": [
                  "accepted",
                  "accept_queue",
                  "pending",
                  "decline_queue",
                  "declined"
                ],
                "description": "Filter by session status (applicable to session searches)."
              }
            }
          },
          "sort": {
            "$ref": "#/components/schemas/SortOptions"
          },
          "expand": {
            "type": "array",
            "items": {
              "type": "string",
              "enum": [
                "translated_fields",
                "subsession_details",
                "linked_sources",
                "composition"
              ]
            },
            "description": "Expand records with additional data. See the `Expand` parameter for `linked_sources` and `composition` details.\n"
          }
        }
      },
      "SessionSearchBody": {
        "type": "object",
        "description": "Search request body for sessions with status filtering.",
        "properties": {
          "filters": {
            "type": "object",
            "properties": {
              "createdAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "updatedAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "status": {
                "type": "string",
                "enum": [
                  "accepted",
                  "accept_queue",
                  "pending",
                  "decline_queue",
                  "declined"
                ]
              },
              "isAbstract": {
                "type": "boolean",
                "description": "Filter to abstract submissions (`true`) or program sessions (`false`)."
              },
              "sessionIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "trackIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                },
                "description": "Match sessions with any of these track IDs (OR). Combined with other filters using AND. Send at least one ID — an empty array is rejected with a 400; to apply no track filter, omit the property."
              },
              "levelIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "formatIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "languageIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "tagIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                },
                "description": "Match sessions tagged with any of these tag IDs (OR). Send at least one ID — an empty array is rejected with a 400."
              }
            }
          },
          "sort": {
            "$ref": "#/components/schemas/SessionSortOptions"
          },
          "expand": {
            "type": "array",
            "items": {
              "type": "string",
              "enum": [
                "translated_fields",
                "subsession_details",
                "linked_sources",
                "composition"
              ]
            }
          }
        }
      },
      "SpeakerSearchBody": {
        "type": "object",
        "description": "Search request body for speakers, including session metadata filters.\nCategorization filters (`trackIds`, `levelIds`, `formatIds`,\n`languageIds`, `tagIds`) match against the speaker's **top-level\nsession** — a speaker on a subsession matches via the subsession's\nparent (root) session, mirroring session search semantics.\n",
        "properties": {
          "filters": {
            "type": "object",
            "properties": {
              "createdAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "updatedAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "status": {
                "type": "string",
                "enum": [
                  "accepted",
                  "accept_queue",
                  "pending",
                  "decline_queue",
                  "declined"
                ]
              },
              "trackIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                },
                "description": "Send at least one ID — an empty array is rejected with a 400; to apply no track filter, omit the property."
              },
              "levelIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "formatIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "languageIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "tagIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              }
            }
          },
          "sort": {
            "$ref": "#/components/schemas/SortOptions"
          },
          "expand": {
            "type": "array",
            "items": {
              "type": "string",
              "enum": [
                "translated_fields"
              ]
            }
          }
        }
      },
      "ParticipantSearchBody": {
        "type": "object",
        "description": "Search request body for participants. Every `SpeakerSearchBody` filter\nis accepted with the same semantics (categorization filters match the\nparticipant's **top-level** session), plus `roleIds`, `roleSlugs` and `email`.\n",
        "properties": {
          "filters": {
            "type": "object",
            "properties": {
              "createdAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "updatedAt": {
                "$ref": "#/components/schemas/DateRangeFilter"
              },
              "status": {
                "type": "string",
                "enum": [
                  "accepted",
                  "accept_queue",
                  "pending",
                  "decline_queue",
                  "declined"
                ],
                "description": "Match participants on sessions with this session status."
              },
              "trackIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                },
                "description": "Send at least one ID — an empty array is rejected with a 400; to apply no track filter, omit the property."
              },
              "levelIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "formatIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "languageIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "tagIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                }
              },
              "roleIds": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "format": "uuid"
                },
                "description": "Return participants holding at least one of these roles\n(standard or custom). Ids come from\n`GET /v1/event/{eventId}/participant-roles`. An empty array is a\n400; omit the property to match every role.\n"
              },
              "roleSlugs": {
                "type": "array",
                "minItems": 1,
                "items": {
                  "type": "string",
                  "minLength": 1,
                  "maxLength": 100
                },
                "description": "Return participants holding at least one role with these slugs —\nthe standard `speaker`, `chairperson`, `moderator`, or a custom\nrole's `slug` from `GET .../participant-roles`. Works on events\nwhose roles have `roleId: null`. Case-insensitive. Combines with\n`roleIds` as AND. An empty array is a 400.\n"
              },
              "email": {
                "type": "string",
                "minLength": 1,
                "maxLength": 320,
                "description": "Exact, case-insensitive match on the contact's email. An\nunknown address returns an empty result set, not an error.\n"
              }
            }
          },
          "sort": {
            "$ref": "#/components/schemas/SortOptions"
          },
          "expand": {
            "type": "array",
            "items": {
              "type": "string",
              "enum": [
                "translated_fields"
              ]
            }
          }
        }
      },
      "Pagination": {
        "type": "object",
        "description": "Pagination metadata returned with POST search responses. The event-settings GET lists return the same numbers under snake_case keys — see `ListPagination`.",
        "properties": {
          "currentPage": {
            "type": "integer",
            "examples": [
              1
            ]
          },
          "pageSize": {
            "type": "integer",
            "examples": [
              25
            ]
          },
          "totalPages": {
            "type": "integer",
            "examples": [
              4
            ]
          },
          "totalResults": {
            "type": "integer",
            "examples": [
              97
            ]
          }
        }
      },
      "ListPagination": {
        "type": "object",
        "description": "Pagination metadata returned by the event-settings GET lists (tags, tracks, levels, formats, rooms, languages, statuses). Same numbers as `Pagination`, snake_case keys — these endpoints are served by a different layer, and the casing is longstanding.",
        "properties": {
          "current_page": {
            "type": "integer",
            "examples": [
              1
            ]
          },
          "page_size": {
            "type": "integer",
            "examples": [
              25
            ]
          },
          "total_pages": {
            "type": "integer",
            "examples": [
              4
            ]
          },
          "total_results": {
            "type": "integer",
            "examples": [
              97
            ]
          }
        }
      },
      "CompositionTargetSummary": {
        "type": "object",
        "description": "Summary of a related session in a composition relationship.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string"
          },
          "title": {
            "type": "string"
          },
          "is_abstract": {
            "type": "boolean"
          }
        }
      },
      "CompositionStatus": {
        "type": "object",
        "description": "Summary of how this session participates in a composition (merge or link).\nAlways present on session responses.\n",
        "properties": {
          "role": {
            "type": "string",
            "enum": [
              "standalone",
              "target",
              "source"
            ],
            "description": "- `standalone` — normal editable record\n- `target` — composite parent with one or more linked sources\n- `source` — linked into another record (still editable)\n"
          },
          "is_linked": {
            "type": "boolean"
          },
          "is_read_only": {
            "type": "boolean",
            "enum": [
              false
            ],
            "description": "Always `false`. Linked sources stay editable; the key is kept for compatibility."
          },
          "source_count": {
            "type": "integer",
            "description": "Number of records merged or linked into this session."
          },
          "target": {
            "allOf": [
              {
                "$ref": "#/components/schemas/CompositionTargetSummary"
              }
            ],
            "nullable": true,
            "description": "Present when `role` is `source`."
          }
        }
      },
      "CompositionSource": {
        "type": "object",
        "properties": {
          "composition_id": {
            "type": "string",
            "format": "uuid"
          },
          "relationship_type": {
            "type": "string",
            "enum": [
              "merged_session",
              "merged_abstract",
              "composed_into_session"
            ]
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string"
          },
          "title": {
            "type": "string"
          },
          "is_abstract": {
            "type": "boolean"
          }
        }
      },
      "CompositionDetail": {
        "type": "object",
        "description": "Full composition graph. Present when `expand=composition`.",
        "properties": {
          "target": {
            "allOf": [
              {
                "$ref": "#/components/schemas/CompositionTargetSummary"
              }
            ],
            "nullable": true
          },
          "sources": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CompositionSource"
            }
          }
        }
      },
      "ContactSessionSummary": {
        "type": "object",
        "description": "Lightweight session summary for contact session lists. Includes\ncomposition summary fields but not the full `composition` graph.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "title": {
            "type": "string"
          },
          "status": {
            "type": "string"
          },
          "custom_status": {
            "type": "string",
            "nullable": true
          },
          "is_abstract": {
            "type": "boolean"
          },
          "composition_status": {
            "$ref": "#/components/schemas/CompositionStatus"
          }
        }
      },
      "OrgContactSessionSummary": {
        "allOf": [
          {
            "$ref": "#/components/schemas/ContactSessionSummary"
          },
          {
            "type": "object",
            "properties": {
              "event_id": {
                "type": "integer",
                "description": "Event the session belongs to."
              }
            }
          }
        ]
      },
      "ContactSessionsResponse": {
        "type": "object",
        "properties": {
          "sessions": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ContactSessionSummary"
            }
          },
          "status": {
            "type": "string",
            "description": "Aggregated contact status derived from linked sessions\n(`accepted`, `pending`, or a single session's status).\n"
          }
        }
      },
      "OrgContactSessionsResponse": {
        "type": "object",
        "properties": {
          "sessions": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/OrgContactSessionSummary"
            }
          },
          "status": {
            "type": "string",
            "description": "Aggregated contact status derived from linked sessions\n(`accepted`, `pending`, or a single session's status).\n"
          }
        }
      },
      "Event": {
        "type": "object",
        "description": "An event on the Sessionboard platform.",
        "properties": {
          "id": {
            "type": "integer",
            "examples": [
              3960
            ]
          },
          "name": {
            "type": "string",
            "examples": [
              "Acme Conference"
            ]
          },
          "timezone": {
            "type": "string",
            "examples": [
              "America/Chicago"
            ]
          },
          "starts_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          },
          "ends_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          },
          "features": {
            "type": "object",
            "properties": {
              "primary_speakers": {
                "type": "boolean"
              },
              "speaker_acceptance": {
                "type": "boolean"
              },
              "translated_fields": {
                "type": "boolean"
              }
            }
          },
          "custom_fields": {
            "type": "array",
            "description": "Present only when `expand=custom_fields` is passed to\n`GET /v1/events`. Empty array when the event has no values.\n",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "integration_mappings": {
            "type": "array",
            "description": "Present only when `expand=integration_mappings` is passed to\n`GET /v1/events`. Conference connector event IDs only — LiveBuzz\n/ apps-engine campaign IDs are not included. Empty array when\nnone are mapped.\n",
            "items": {
              "$ref": "#/components/schemas/EventIntegrationMapping"
            }
          }
        }
      },
      "EventIntegrationMapping": {
        "type": "object",
        "description": "A conference integration's identifier for this Sessionboard event.",
        "properties": {
          "name": {
            "type": "string",
            "description": "Display name (for example `Cvent`, `Grip`).",
            "examples": [
              "Cvent"
            ]
          },
          "source": {
            "type": "string",
            "description": "Integration key from `Integration_Event_Mapping_Union` (table name minus `Integration_` / `_Event_Mappings`, lowercased). Multi-word vendors use underscores, e.g. `expo_platform`.\n",
            "examples": [
              "cvent",
              "expo_platform"
            ]
          },
          "external_event_id": {
            "type": "string",
            "description": "Vendor event id, always a string.",
            "examples": [
              "a1b2c3d4-e5f6-7890-abcd-ef1234567890"
            ]
          }
        }
      },
      "Session": {
        "type": "object",
        "description": "A session within an event (e.g., talk, workshop, panel, or CFP abstract submission).",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "title": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "status": {
            "type": "string",
            "enum": [
              "accepted",
              "accept_queue",
              "pending",
              "decline_queue",
              "declined"
            ]
          },
          "custom_status_id": {
            "type": "string"
          },
          "custom_status": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "name": {
                "type": "string"
              }
            }
          },
          "starts_at": {
            "type": "string",
            "format": "date-time"
          },
          "ends_at": {
            "type": "string",
            "format": "date-time"
          },
          "is_public": {
            "type": "boolean"
          },
          "is_abstract": {
            "type": "boolean",
            "description": "True for CFP abstract submissions; false for program sessions."
          },
          "composition_status": {
            "$ref": "#/components/schemas/CompositionStatus"
          },
          "composition": {
            "$ref": "#/components/schemas/CompositionDetail",
            "description": "Present when `expand=composition` is requested."
          },
          "external_url": {
            "type": "string",
            "format": "uri"
          },
          "client_session_id": {
            "type": "string"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "ceu_credits": {
            "type": "number",
            "format": "float"
          },
          "capacity": {
            "type": "integer"
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "translated_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranslatedField"
            }
          },
          "speakers": {
            "type": "array",
            "description": "Legacy junction-table speakers (`Session_Speakers`). Retained for backwards\ncompatibility. Each entry includes `participant_role` when the event has\nSessions 2.0 roles configured. Prefer `participants` for new integrations\nthat need custom program roles or a single flat participant list.\n",
            "items": {
              "$ref": "#/components/schemas/SessionSpeaker"
            }
          },
          "chairpersons": {
            "type": "array",
            "description": "Legacy junction-table chairpersons (`Session_Chairpersons`). See `speakers`\nfor migration guidance.\n",
            "items": {
              "$ref": "#/components/schemas/SessionSpeaker"
            }
          },
          "moderators": {
            "type": "array",
            "description": "Legacy junction-table moderators (`Session_Moderators`). See `speakers`\nfor migration guidance.\n",
            "items": {
              "$ref": "#/components/schemas/SessionSpeaker"
            }
          },
          "participants": {
            "type": "array",
            "description": "Flat list of session participants from the Sessions 2.0 data model\n(`Session_Participants` + `Session_Roles`). Always returned on session\nsearch and get (no expand flag). Includes custom program roles (for example\nAuthor, Panelist) in addition to the legacy speaker/chairperson/moderator\njunction tables. Legacy arrays above remain for backwards compatibility;\neach legacy entry also includes `participant_role` when event roles are\nconfigured. Contact profile fields (`photo_url`, `company_name`, `title`,\n`address_country`, etc.) are hydrated from the contact record in the event's\ndefault language without requiring expand.\n",
            "items": {
              "$ref": "#/components/schemas/SessionParticipant"
            }
          },
          "sponsors": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SessionSponsor"
            }
          },
          "exhibitors": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SessionExhibitor"
            }
          },
          "content": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Content"
            }
          },
          "tags": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Tag"
            }
          },
          "language": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Language"
              }
            ],
            "description": "Assigned session language. Includes `id`, `event_id`, `name`, `order`,\n`created_at`, and `updated_at` when set. Unassigned values are an\nempty object `{}` on `POST` session search responses and `null` on\nCRUD proxy responses (`GET` list, create, update, restore).\n"
          },
          "track": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Track"
              }
            ],
            "description": "Assigned session track. Includes `id`, `event_id`, `name`, `color`,\n`order`, `created_at`, and `updated_at` when set. Unassigned values\nare `{}` on `POST` session search and `null` on CRUD proxy responses.\n"
          },
          "level": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Level"
              }
            ],
            "description": "Assigned session level. Includes `id`, `name`, `order`, `created_at`,\nand `updated_at` when set (no `event_id` on nested objects). Unassigned\nvalues are `{}` on `POST` session search and `null` on CRUD proxy responses.\n"
          },
          "format": {
            "type": "object",
            "description": "Assigned session format. Nested session objects include only `id` and\n`name` (not the full standalone `Format` schema).\n",
            "properties": {
              "id": {
                "type": "string"
              },
              "name": {
                "type": "string"
              }
            }
          },
          "room": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Room"
              }
            ],
            "description": "Assigned room when `location` is `room`. Includes `id`, `name`,\n`order`, `capacity`, `created_at`, and `updated_at` when set. Omitted\nwhen location is `external` or unset (`{}` on `POST` search, `null` on\nCRUD proxy). `event_id` is not included on nested room objects.\n"
          },
          "subsessions": {
            "type": "array",
            "description": "Subsessions of this parent session. Each item defaults to the\nminimal `Subsession` shape; pass `expand=subsession_details` to\nreceive the full `SubsessionDetailed` shape on every subsession\nin the array. Composition fields (`is_abstract`,\n`composition_status`, optional `composition`) are inherited from\nthe parent session.\n\nItems are returned in the order set by the event admin\n(`subsession_order`), falling back to subsession number and then\nstart time for subsessions that have never been reordered.\n",
            "items": {
              "oneOf": [
                {
                  "$ref": "#/components/schemas/Subsession"
                },
                {
                  "$ref": "#/components/schemas/SubsessionDetailed"
                }
              ]
            }
          },
          "admin_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Deep link to this entity in the Sessionboard admin UI."
          }
        },
        "examples": [
          {
            "id": "497f6eca-6276-4993-bfeb-53cbbbba6f08",
            "friendly_id": "SESS-8",
            "friendly_id_raw": 8,
            "title": "Networking",
            "description": "<p>Networking session description</p>",
            "status": "accepted",
            "starts_at": "2024-03-15T09:00:00Z",
            "ends_at": "2024-03-15T10:00:00Z",
            "is_public": true,
            "created_at": "2024-01-10T14:30:00Z",
            "updated_at": "2024-03-01T09:15:00Z",
            "ceu_credits": 1.5,
            "capacity": 200,
            "language": {
              "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
              "event_id": 42,
              "name": "English",
              "order": 0,
              "created_at": "2024-01-01T00:00:00Z",
              "updated_at": "2024-01-01T00:00:00Z"
            },
            "track": {
              "id": "b2c3d4e5-f6a7-8901-bcde-f12345678901",
              "event_id": 42,
              "name": "Artificial Intelligence & ML",
              "color": "#329af0",
              "order": 1,
              "created_at": "2024-01-01T00:00:00Z",
              "updated_at": "2024-01-01T00:00:00Z"
            },
            "level": {
              "id": "c3d4e5f6-a7b8-9012-cdef-123456789012",
              "name": "Beginner",
              "order": 2,
              "created_at": "2024-01-01T00:00:00Z",
              "updated_at": "2024-01-01T00:00:00Z"
            },
            "format": {
              "id": "d4e5f6a7-b8c9-0123-def0-234567890123",
              "name": "Session"
            },
            "room": {
              "id": "e5f6a7b8-c9d0-1234-ef01-345678901234",
              "name": "Workshop Room 1",
              "order": 3,
              "capacity": 120,
              "created_at": "2024-01-01T00:00:00Z",
              "updated_at": "2024-01-01T00:00:00Z"
            },
            "tags": [],
            "speakers": [],
            "content": [],
            "custom_fields": [],
            "admin_url": "https://app.sessionboard.com/event/42/sessions/497f6eca-6276-4993-bfeb-53cbbbba6f08"
          }
        ]
      },
      "SessionStatus": {
        "type": "object",
        "description": "A lightweight representation of a session's status, including\nsoft-deleted sessions. Parent rows additionally include a\n`subsessions` array with the same minimal status-focused shape for\neach child subsession. Subsession rows that appear in the flat list\nreturn an empty `subsessions` array.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "status": {
            "type": "string"
          },
          "custom_status_id": {
            "type": "string",
            "format": "uuid",
            "nullable": true
          },
          "custom_status": {
            "$ref": "#/components/schemas/SessionCustomStatus"
          },
          "is_abstract": {
            "type": "boolean"
          },
          "composition_status": {
            "$ref": "#/components/schemas/CompositionStatus"
          },
          "deleted_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "subsessions": {
            "type": "array",
            "description": "Empty for subsession rows. Populated with `SubsessionStatus` items for parent rows, in the admin-defined order (`subsession_order`, falling back to subsession number and start time).",
            "items": {
              "$ref": "#/components/schemas/SubsessionStatus"
            }
          }
        }
      },
      "Contact": {
        "type": "object",
        "description": "A contact (speaker, attendee, or organizational contact) in Sessionboard.",
        "properties": {
          "id": {
            "type": "string"
          },
          "friendly_id": {
            "type": "string"
          },
          "full_name": {
            "type": "string"
          },
          "first_name": {
            "type": "string"
          },
          "last_name": {
            "type": "string"
          },
          "email": {
            "type": "string"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          },
          "photo_url": {
            "type": "string"
          },
          "company_name": {
            "type": "string"
          },
          "title": {
            "type": "string"
          },
          "about": {
            "type": "string"
          },
          "phone_home": {
            "type": "string"
          },
          "phone_mobile": {
            "type": "string"
          },
          "address_line_1": {
            "type": "string"
          },
          "address_line_2": {
            "type": "string"
          },
          "address_city": {
            "type": "string"
          },
          "address_state": {
            "type": "string"
          },
          "address_postal_code": {
            "type": "string"
          },
          "address_country": {
            "type": "string"
          },
          "website_url": {
            "type": "string"
          },
          "linkedin_url": {
            "type": "string"
          },
          "twitter_url": {
            "type": "string"
          },
          "facebook_url": {
            "type": "string"
          },
          "honorific": {
            "type": "string"
          },
          "salutation": {
            "type": "string"
          },
          "pronouns": {
            "type": "string"
          },
          "gender": {
            "type": "string"
          },
          "past_companies": {
            "type": "string"
          },
          "educational_affiliation": {
            "type": "string"
          },
          "highest_level_of_education": {
            "type": "string"
          },
          "ethnicity": {
            "type": "string"
          },
          "languages": {
            "type": "string"
          },
          "speaker_score": {
            "type": "string"
          },
          "organization_contact": {
            "type": "string"
          },
          "speaker_fee": {
            "type": "string"
          },
          "availability": {
            "type": "string"
          },
          "preferred_session_format": {
            "type": "string"
          },
          "annual_revenue": {
            "type": "string"
          },
          "headcount": {
            "type": "string"
          },
          "years_in_operation": {
            "type": "string"
          },
          "organization_structure": {
            "type": "string"
          },
          "industry": {
            "type": "string"
          },
          "global_region": {
            "type": "string"
          },
          "audience_type": {
            "type": "string"
          },
          "target_age_range": {
            "type": "string"
          },
          "topic_expertise": {
            "type": "string"
          },
          "brand": {
            "type": "string"
          },
          "translated_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranslatedField"
            }
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "admin_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Deep link to this entity in the Sessionboard admin UI."
          }
        },
        "examples": [
          {
            "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
            "friendly_id": "SPK-42",
            "full_name": "Dr. Jane Smith",
            "first_name": "Jane",
            "last_name": "Smith",
            "email": "jane.smith@university.edu",
            "created_at": "2023-11-01T10:00:00Z",
            "updated_at": "2024-02-15T16:30:00Z",
            "photo_url": "https://cdn.sessionboard.com/photos/jane-smith.jpg",
            "company_name": "State University",
            "title": "Professor of Computer Science",
            "about": "Dr. Smith is a leading researcher in distributed systems.",
            "address_city": "Austin",
            "address_state": "TX",
            "address_country": "US",
            "honorific": "Dr.",
            "pronouns": "she/her",
            "topic_expertise": "Distributed Systems, Cloud Computing",
            "custom_fields": [],
            "translated_fields": []
          }
        ]
      },
      "SessionSpeaker": {
        "type": "object",
        "description": "A contact embedded on a session (speaker, chairperson, moderator, or other\nprogram role). Standard contact profile fields (`photo_url`, `company_name`,\n`title`, `address_country`, etc.) are hydrated from the contact's module field\nvalues in the event's default language. No expand is required for these fields;\nuse `expand=translated_fields` for other locales.\n",
        "properties": {
          "id": {
            "type": "string"
          },
          "participant_role": {
            "$ref": "#/components/schemas/ParticipantRole",
            "description": "The event's configured program role for this participant (Sessions 2.0).\n`name` and `slug` reflect the configured `Session_Roles` record (for example\nAuthor, Panelist). `core_role` is the legacy junction category mapping only\n(`speaker`, `chairperson`, `moderator`) and must not be used as the display\nrole label. Present on legacy `speakers`, `chairpersons`, and `moderators`\nentries when the event has `Session_Roles` configured.\n"
          },
          "friendly_id": {
            "type": "string"
          },
          "full_name": {
            "type": "string"
          },
          "first_name": {
            "type": "string"
          },
          "last_name": {
            "type": "string"
          },
          "email": {
            "type": "string"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          },
          "photo_url": {
            "type": "string"
          },
          "company_name": {
            "type": "string"
          },
          "title": {
            "type": "string"
          },
          "about": {
            "type": "string"
          },
          "phone_home": {
            "type": "string"
          },
          "phone_mobile": {
            "type": "string"
          },
          "address_line_1": {
            "type": "string"
          },
          "address_line_2": {
            "type": "string"
          },
          "address_city": {
            "type": "string"
          },
          "address_state": {
            "type": "string"
          },
          "address_postal_code": {
            "type": "string"
          },
          "address_country": {
            "type": "string"
          },
          "website_url": {
            "type": "string"
          },
          "linkedin_url": {
            "type": "string"
          },
          "twitter_url": {
            "type": "string"
          },
          "facebook_url": {
            "type": "string"
          },
          "instagram_url": {
            "type": "string"
          },
          "snapchat_username": {
            "type": "string"
          },
          "tiktok_username": {
            "type": "string"
          },
          "translated_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranslatedField"
            }
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          }
        }
      },
      "ParticipantRole": {
        "type": "object",
        "description": "An event-configured session participant role (`Session_Roles`). Use `name` (or\n`slug` for programmatic matching) as the participant's role label. `core_role`\nis the legacy junction category only.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid",
            "description": "Session_Roles.id"
          },
          "slug": {
            "type": "string",
            "description": "Stable programmatic identifier for the role within the event."
          },
          "name": {
            "type": "string",
            "description": "Display name (singular)."
          },
          "name_plural": {
            "type": "string",
            "description": "Display name (plural)."
          },
          "core_role": {
            "type": "string",
            "enum": [
              "speaker",
              "chairperson",
              "moderator"
            ],
            "description": "Legacy junction category this role maps to for integrations."
          }
        }
      },
      "SessionParticipant": {
        "allOf": [
          {
            "$ref": "#/components/schemas/SessionSpeaker"
          },
          {
            "type": "object",
            "description": "Sessions 2.0 participant row. Includes the same contact profile fields as\n`SessionSpeaker`. `participant_role` is always present (sourced from\n`Session_Roles`).\n",
            "properties": {
              "session_participant_id": {
                "type": "string",
                "format": "uuid",
                "description": "Primary key of the `Session_Participants` row."
              },
              "acceptance_status": {
                "type": "string",
                "enum": [
                  "pending",
                  "accepted",
                  "declined",
                  "not_accepted"
                ],
                "description": "The participant's answer to their acceptance invitation. Present only\nwhen the event has Participant Acceptance turned on\n(`features.speaker_acceptance`).\n"
              },
              "acceptance_invite_sent_at": {
                "type": [
                  "string",
                  "null"
                ],
                "format": "date-time",
                "description": "When the acceptance invitation for this role was last sent, or `null`\nif it has not been sent. Present only when the event has Participant\nAcceptance turned on.\n"
              }
            }
          }
        ]
      },
      "ParticipantRoleAssignment": {
        "type": "object",
        "description": "One role a participant holds on the event, with the sessions it holds\nit on. Returned inside `Participant.roles`.\n",
        "required": [
          "roleId",
          "roleName",
          "slug",
          "coreRole",
          "isCustom",
          "sessionIds"
        ],
        "properties": {
          "roleId": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid",
            "description": "The role's id — the value to pass in the `roleIds` filter and the\n`id` returned by `GET /v1/event/{eventId}/participant-roles`.\n`null` only for a standard role on an event whose roles have not\nbeen created yet (see the endpoint description).\n"
          },
          "roleName": {
            "type": "string",
            "description": "Display name of the role (singular), e.g. `Speaker`, `Panelist`."
          },
          "slug": {
            "type": "string",
            "description": "Stable programmatic identifier for the role within the event."
          },
          "coreRole": {
            "type": "string",
            "enum": [
              "speaker",
              "chairperson",
              "moderator"
            ],
            "description": "The standard category the role maps to. Not a display label."
          },
          "isCustom": {
            "type": "boolean",
            "description": "`true` for a role the organizer added; `false` for Speaker, Chairperson and Moderator."
          },
          "sessionIds": {
            "type": "array",
            "items": {
              "type": "string",
              "format": "uuid"
            },
            "description": "Ids of the sessions (including subsessions) on which the contact holds this role."
          }
        }
      },
      "Participant": {
        "allOf": [
          {
            "$ref": "#/components/schemas/Contact"
          },
          {
            "type": "object",
            "description": "A contact holding at least one session role on the event. Every\n`Contact` field is present with the same values `POST /speakers`\nreturns; `roles` is appended after them.\n",
            "required": [
              "roles"
            ],
            "properties": {
              "roles": {
                "type": "array",
                "description": "Every role the contact holds on the event and the sessions it\nholds each one on. Always the contact's complete set — not\nnarrowed by the request filters. Ordered by the role's\nconfigured sort order.\n",
                "items": {
                  "$ref": "#/components/schemas/ParticipantRoleAssignment"
                }
              }
            }
          }
        ],
        "examples": [
          {
            "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
            "friendly_id": "SPK-42",
            "full_name": "Dr. Jane Smith",
            "first_name": "Jane",
            "last_name": "Smith",
            "email": "jane.smith@university.edu",
            "created_at": "2023-11-01T10:00:00Z",
            "updated_at": "2024-02-15T16:30:00Z",
            "company_name": "State University",
            "title": "Professor of Computer Science",
            "custom_fields": [],
            "roles": [
              {
                "roleId": "84bd12e5-d5ec-4c64-a604-4051e06c8dc2",
                "roleName": "Speaker",
                "slug": "speaker",
                "coreRole": "speaker",
                "isCustom": false,
                "sessionIds": [
                  "04efb360-2b15-44db-b639-4035fae2772c"
                ]
              },
              {
                "roleId": "4efeb845-050f-4002-9496-cb586cdf10f2",
                "roleName": "Moderator",
                "slug": "moderator",
                "coreRole": "moderator",
                "isCustom": false,
                "sessionIds": [
                  "26e465fc-1fb1-4c04-af52-f4d6314dfca4"
                ]
              },
              {
                "roleId": "52d60237-19db-4bda-a116-8b9fcb6750e9",
                "roleName": "Panelist",
                "slug": "panelist",
                "coreRole": "speaker",
                "isCustom": true,
                "sessionIds": [
                  "140b8e82-41ca-444e-82ab-f7dd1011e95b",
                  "2c198cce-adff-4fb2-81e1-319b601d564b"
                ]
              }
            ]
          }
        ]
      },
      "EventParticipantRole": {
        "type": "object",
        "description": "A participant role configured on an event, as returned by\n`GET /v1/event/{eventId}/participant-roles`.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid",
            "description": "Use as a `roleIds` filter value on `POST /v1/event/{eventId}/participants`."
          },
          "name": {
            "type": "string",
            "description": "Display name (singular)."
          },
          "name_plural": {
            "type": "string",
            "description": "Display name (plural)."
          },
          "slug": {
            "type": "string",
            "description": "Stable programmatic identifier within the event."
          },
          "core_role": {
            "type": "string",
            "enum": [
              "speaker",
              "chairperson",
              "moderator"
            ],
            "description": "The standard category the role maps to. Not a display label."
          },
          "is_custom": {
            "type": "boolean",
            "description": "`true` for a role the organizer added; `false` for the three standard roles."
          },
          "sort_order": {
            "type": "integer",
            "description": "Position in the Sessions settings page; results are returned in this order."
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "Sponsor": {
        "type": "object",
        "description": "A sponsor associated with an event.",
        "properties": {
          "id": {
            "type": "string"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "logo_image_url": {
            "type": "string"
          },
          "banner_image_url": {
            "type": "string"
          },
          "phone": {
            "type": "string"
          },
          "address_line_1": {
            "type": "string"
          },
          "address_line_2": {
            "type": "string"
          },
          "address_city": {
            "type": "string"
          },
          "address_state": {
            "type": "string"
          },
          "address_postal_code": {
            "type": "string"
          },
          "address_coutnry": {
            "type": "string",
            "description": "Country (note: field name contains a known typo preserved for backwards compatibility)."
          },
          "facebook_url": {
            "type": "string"
          },
          "instagram_url": {
            "type": "string"
          },
          "linkedin_url": {
            "type": "string"
          },
          "snapchat_username": {
            "type": "string"
          },
          "tiktok_username": {
            "type": "string"
          },
          "twitter_url": {
            "type": "string"
          },
          "website_url": {
            "type": "string"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "translated_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranslatedField"
            }
          },
          "contacts": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AccountContact"
            }
          },
          "admin_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Deep link to this entity in the Sessionboard admin UI."
          }
        },
        "examples": [
          {
            "id": "b2c3d4e5-f6a7-8901-bcde-f12345678901",
            "friendly_id": "SPON-3",
            "friendly_id_raw": 3,
            "name": "TechCorp Global",
            "description": "Platinum sponsor and technology partner.",
            "logo_image_url": "https://cdn.sessionboard.com/logos/techcorp.png",
            "phone": "+1-555-0100",
            "address_city": "San Francisco",
            "address_state": "CA",
            "address_coutnry": "US",
            "website_url": "https://www.techcorp.example.com",
            "linkedin_url": "https://www.linkedin.com/company/techcorp",
            "created_at": "2024-01-05T08:00:00Z",
            "updated_at": "2024-02-20T12:00:00Z",
            "custom_fields": [],
            "translated_fields": [],
            "contacts": []
          }
        ]
      },
      "SessionSponsor": {
        "type": "object",
        "description": "A sponsor associated with a session. Same shape as Sponsor.",
        "properties": {
          "id": {
            "type": "string"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "logo_image_url": {
            "type": "string"
          },
          "banner_image_url": {
            "type": "string"
          },
          "phone": {
            "type": "string"
          },
          "address_line_1": {
            "type": "string"
          },
          "address_line_2": {
            "type": "string"
          },
          "address_city": {
            "type": "string"
          },
          "address_state": {
            "type": "string"
          },
          "address_postal_code": {
            "type": "string"
          },
          "address_coutnry": {
            "type": "string"
          },
          "facebook_url": {
            "type": "string"
          },
          "instagram_url": {
            "type": "string"
          },
          "linkedin_url": {
            "type": "string"
          },
          "snapchat_username": {
            "type": "string"
          },
          "tiktok_username": {
            "type": "string"
          },
          "twitter_url": {
            "type": "string"
          },
          "website_url": {
            "type": "string"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "translated_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranslatedField"
            }
          },
          "contacts": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AccountContact"
            }
          }
        }
      },
      "Exhibitor": {
        "type": "object",
        "description": "An exhibitor associated with an event.",
        "properties": {
          "id": {
            "type": "string"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "logo_image_url": {
            "type": "string"
          },
          "banner_image_url": {
            "type": "string"
          },
          "phone": {
            "type": "string"
          },
          "address_line_1": {
            "type": "string"
          },
          "address_line_2": {
            "type": "string"
          },
          "address_city": {
            "type": "string"
          },
          "address_state": {
            "type": "string"
          },
          "address_postal_code": {
            "type": "string"
          },
          "address_coutnry": {
            "type": "string",
            "description": "Country (note: field name contains a known typo preserved for backwards compatibility)."
          },
          "facebook_url": {
            "type": "string"
          },
          "instagram_url": {
            "type": "string"
          },
          "linkedin_url": {
            "type": "string"
          },
          "snapchat_username": {
            "type": "string"
          },
          "tiktok_username": {
            "type": "string"
          },
          "twitter_url": {
            "type": "string"
          },
          "website_url": {
            "type": "string"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "translated_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranslatedField"
            }
          },
          "contacts": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AccountContact"
            }
          },
          "admin_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Deep link to this entity in the Sessionboard admin UI."
          }
        },
        "examples": [
          {
            "id": "c3d4e5f6-a7b8-9012-cdef-123456789012",
            "friendly_id": "EXH-7",
            "friendly_id_raw": 7,
            "name": "InnovateTech Labs",
            "description": "Showcasing next-generation event technology solutions.",
            "logo_image_url": "https://cdn.sessionboard.com/logos/innovatetech.png",
            "address_city": "Chicago",
            "address_state": "IL",
            "address_coutnry": "US",
            "website_url": "https://www.innovatetech.example.com",
            "created_at": "2024-01-12T10:00:00Z",
            "updated_at": "2024-03-01T14:00:00Z",
            "custom_fields": [],
            "translated_fields": [],
            "contacts": []
          }
        ]
      },
      "SessionExhibitor": {
        "type": "object",
        "description": "An exhibitor associated with a session. Same shape as Exhibitor.",
        "properties": {
          "id": {
            "type": "string"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "logo_image_url": {
            "type": "string"
          },
          "banner_image_url": {
            "type": "string"
          },
          "phone": {
            "type": "string"
          },
          "address_line_1": {
            "type": "string"
          },
          "address_line_2": {
            "type": "string"
          },
          "address_city": {
            "type": "string"
          },
          "address_state": {
            "type": "string"
          },
          "address_postal_code": {
            "type": "string"
          },
          "address_coutnry": {
            "type": "string"
          },
          "facebook_url": {
            "type": "string"
          },
          "instagram_url": {
            "type": "string"
          },
          "linkedin_url": {
            "type": "string"
          },
          "snapchat_username": {
            "type": "string"
          },
          "tiktok_username": {
            "type": "string"
          },
          "twitter_url": {
            "type": "string"
          },
          "website_url": {
            "type": "string"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "translated_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranslatedField"
            }
          },
          "contacts": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AccountContact"
            }
          }
        }
      },
      "AccountContact": {
        "type": "object",
        "description": "A contact associated with a sponsor or exhibitor account.",
        "properties": {
          "id": {
            "type": "string"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "full_name": {
            "type": "string"
          },
          "first_name": {
            "type": "string"
          },
          "last_name": {
            "type": "string"
          },
          "email": {
            "type": "string"
          },
          "photo_url": {
            "type": "string"
          },
          "company_name": {
            "type": "string"
          },
          "title": {
            "type": "string"
          },
          "about": {
            "type": "string"
          },
          "is_primary": {
            "type": "boolean"
          },
          "contact_created_at": {
            "type": "string"
          },
          "contact_updated_at": {
            "type": "string"
          },
          "relationship_created_at": {
            "type": "string"
          },
          "relationship_updated_at": {
            "type": "string"
          }
        }
      },
      "CustomFieldValue": {
        "type": "object",
        "description": "A custom field value attached to a record.",
        "properties": {
          "id": {
            "type": "string"
          },
          "name": {
            "type": "string"
          },
          "value": {
            "type": [
              "string",
              "boolean",
              "null"
            ],
            "description": "The formatted field value, or `null` when the field is empty.\nNumeric field types (`number`, `currency`, `percent`, `quantity`,\n`formula`) serialize a stored zero as its formatted value (for\nexample `\"0\"`) — `null` means the field has no value, not that\nthe value is zero.\n\n`checkbox` fields serialize as the strings `\"Yes\"` (checked) and\n`\"No\"` (explicitly unchecked); a checkbox that was never set is\n`null`. Writes take boolean `true` / `false`.\n\n`datetime` fields serialize as ISO 8601. On event custom fields\n(`GET /v1/events?expand=custom_fields`) the value is event-local\ntime with the event's UTC offset (for example\n`2026-08-15T09:00:00-03:00`), falling back to the raw UTC\ninstant (`2026-08-15T12:00:00.000Z`) when the event has no valid\ntimezone. On session, speaker, sponsor, and exhibitor custom\nfields the value is the raw UTC instant. Date-only fields are\nunaffected.\n"
          },
          "type": {
            "type": "string"
          },
          "internal_name": {
            "type": "string"
          },
          "created_at": {
            "type": "string"
          }
        }
      },
      "TranslatedField": {
        "type": "object",
        "description": "A translated version of a field value.",
        "properties": {
          "id": {
            "type": "string"
          },
          "name": {
            "type": "string"
          },
          "type": {
            "type": "string"
          },
          "parent_field_id": {
            "type": "string"
          },
          "parent_field_source": {
            "type": "string"
          },
          "parent_field_name": {
            "type": "string"
          },
          "parent_field_internal_name": {
            "type": "string"
          },
          "translated_language": {
            "type": "string"
          },
          "value": {
            "type": "string"
          }
        }
      },
      "TranslatedFieldWrite": {
        "type": "object",
        "description": "Write shape for `translated_fields` on create/update. Same identifying\nkeys as the read `TranslatedField` object; extra read-only properties\n(`id`, `name`, `parent_field_id`, …) are ignored if sent.\n\nValidation (applies before anything is written — an invalid entry fails\nthe whole request with `400` `VALIDATION_ERROR` and nothing is\npartially saved):\n- `translated_fields` must be an array of these objects.\n- Every entry must include a non-empty `translated_language`.\n- `translated_language` must be one of the event's enabled locales\n  (the event default plus enabled language variants, e.g. `en_US`,\n  `ar`). The error message lists the enabled locales.\n",
        "required": [
          "parent_field_internal_name",
          "translated_language"
        ],
        "properties": {
          "parent_field_internal_name": {
            "type": "string"
          },
          "translated_language": {
            "type": "string",
            "description": "Locale code for the language variant (for example `fr` or `ar`).\nMust be enabled on the event; otherwise the request fails with `400`.\n"
          },
          "value": {
            "description": "Value for that locale. Same type as the parent field."
          }
        }
      },
      "Content": {
        "type": "object",
        "description": "A content attachment (file, document, or media) associated with a session.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "url": {
            "type": "string",
            "format": "uri"
          },
          "title": {
            "type": "string"
          },
          "filename": {
            "type": "string"
          },
          "size": {
            "type": "integer"
          },
          "mimetype": {
            "type": "string"
          },
          "type": {
            "type": "string",
            "nullable": true,
            "description": "Organizer-facing file type, e.g. `presentation`, `handout`,\n`poster`, or `holding_slide` for slides generated by Sessionboard.\nFilterable with `?type=` on the list endpoint.\n",
            "example": "holding_slide"
          },
          "label": {
            "type": "string",
            "nullable": true,
            "description": "Display label shown on the session's Files tab, e.g. `Holding Slide`.",
            "example": "Holding Slide"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "assigned_participant_id": {
            "type": "string",
            "format": "uuid",
            "nullable": true,
            "description": "Contact UUID of the session participant this file is assigned to."
          },
          "assigned_participant_email": {
            "type": "string",
            "format": "email",
            "nullable": true
          },
          "assigned_participant_name": {
            "type": "string",
            "nullable": true
          },
          "content_slot_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid",
            "description": "The upload slot this file answers — see\n`GET /v1/event/{eventId}/content-slots`. Present only while the\nevent uses upload slots; `null` for events on a single file\nrequest, and for files uploaded before slots existed or outside\nany slot.\n"
          }
        }
      },
      "ContentSlot": {
        "type": "object",
        "description": "One file an event asks its speakers for (SB \"upload slot\"). Slots are\nconfigured under Program → Settings → Files; `session_filters` and\nrole restrictions are internal and not exposed.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "name": {
            "type": "string",
            "description": "The name speakers see, e.g. \"Poster\"."
          },
          "content_type": {
            "type": "string",
            "enum": [
              "poster",
              "presentation",
              "handout",
              "abstract",
              "custom"
            ],
            "description": "What kind of file the slot collects. Poster galleries read `poster` slots."
          },
          "description": {
            "type": [
              "string",
              "null"
            ],
            "description": "Instructions shown to speakers above the drop zone."
          },
          "due_date": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "Deadline shown to speakers. `null` means no deadline."
          },
          "due_date_extended": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "Later date the drop zone stays open until, if the organizer set one."
          },
          "allowed_file_types": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Accepted type keys (`pdf`, `ppt`, `word`, `excel`, `image`, `png`,\n`jpeg`, `gif`, `svg`, `video`, `mp4`, `audio`, `zip`, `csv`,\n`text`). An empty array accepts any type.\n"
          },
          "required": {
            "type": "boolean",
            "description": "Whether the slot counts as missing until a file is uploaded."
          },
          "min_files": {
            "type": [
              "integer",
              "null"
            ]
          },
          "max_files": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Maximum files per session; `null` means unlimited."
          },
          "allow_after_deadline": {
            "type": "boolean",
            "description": "Whether uploads are still accepted after the deadline."
          },
          "order": {
            "type": "integer",
            "description": "Position in the list speakers see (0-based)."
          },
          "is_active": {
            "type": "boolean",
            "description": "`false` for archived slots (only returned with `include_archived=true`)."
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "ContentSlotListResponse": {
        "type": "object",
        "properties": {
          "data": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ContentSlot"
            }
          }
        }
      },
      "Tag": {
        "type": "object",
        "description": "An event taxonomy tag that can be applied to sessions.\n\nThe list, create, and update endpoints return `type`, `color`, and\n`order`; tags nested inside a `Session` response and the search\nendpoint (`POST /tags`) return the identifying fields only.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "type": {
            "type": "string",
            "enum": [
              "tag"
            ]
          },
          "name": {
            "type": "string"
          },
          "color": {
            "type": "string",
            "nullable": true
          },
          "order": {
            "type": "integer",
            "nullable": true
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          }
        }
      },
      "Track": {
        "type": "object",
        "description": "A session track (e.g., a conference track or topic area).\n\nWhen nested inside a `Session` response, includes `event_id`. Standalone\nmetadata list and search endpoints (`GET`/`POST /tracks`) omit `event_id`\nbecause the event is implicit from the URL.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "event_id": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "color": {
            "type": "string"
          },
          "order": {
            "type": "integer"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          }
        }
      },
      "Language": {
        "type": "object",
        "description": "A language configured for an event.\n\nWhen nested inside a `Session` response, includes `event_id`. Standalone\nmetadata list and search endpoints (`GET`/`POST /languages`) omit\n`event_id` because the event is implicit from the URL.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "event_id": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "order": {
            "type": "integer"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          }
        }
      },
      "Format": {
        "type": "object",
        "description": "A session format (e.g., Workshop, Panel, Keynote).",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "event_id": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "order": {
            "type": "integer"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          }
        }
      },
      "Level": {
        "type": "object",
        "description": "A session difficulty level (e.g., Beginner, Intermediate, Advanced).",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "name": {
            "type": "string"
          },
          "order": {
            "type": "integer"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          }
        }
      },
      "Room": {
        "type": "object",
        "description": "A room or venue location for sessions. When nested inside a `Session`\nresponse, `room` is only populated when the session `location` is\n`room` (not for external URLs).\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "name": {
            "type": "string"
          },
          "order": {
            "type": "integer"
          },
          "capacity": {
            "type": "integer",
            "nullable": true,
            "description": "Maximum room capacity. Returned on nested session `room` objects and\nstandalone room list/search endpoints.\n"
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          }
        }
      },
      "Subsession": {
        "type": "object",
        "description": "A subsession nested within a parent session. This is the default\nminimal shape returned inside `parent.subsessions[]` when the\n`subsession_details` expand value is not requested.\n\nTo receive the full parent-shape parity (`status`, `custom_status`,\n`custom_fields`, `chairpersons`, `moderators`, `sponsors`,\n`exhibitors`, `tags`, `language`, `track`, `level`, `room`, etc.),\npass `expand=subsession_details` on the GET or POST search request.\nSee the `SubsessionDetailed` schema.\n\n`is_abstract`, `composition_status`, and optional `composition`\n(when `expand=composition`) are inherited from the parent session.\n\nAlternatively, call `GET /v1/event/{eventId}/sessions/{sessionId}`\nwith the subsession's UUID directly — the endpoint always returns the\nfull session shape at the top level.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string",
            "description": "Human-readable id formatted as `<event-prefix>-<parent-friendly-id>-<subsession-number>` (or `<event-prefix>-<subsession-friendly-id>` when the event has `show_subsession_friendly_id` enabled)."
          },
          "friendly_id_raw": {
            "type": "integer",
            "description": "Underlying numeric friendly id (the suffix of `friendly_id`)."
          },
          "parent_session_friendly_id": {
            "type": "string",
            "description": "Human-readable friendly id of the parent session, e.g. `SESS-3370`."
          },
          "parent_session_friendly_id_raw": {
            "type": "integer",
            "description": "Numeric friendly id of the parent session."
          },
          "subsession_order": {
            "type": "integer",
            "nullable": true,
            "description": "Admin-defined position among the parent session's subsessions; subsessions are returned in this order, falling back to subsession number and start time. `null` when the parent's subsessions have never been reordered."
          },
          "title": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "starts_at": {
            "type": "string",
            "format": "date-time"
          },
          "ends_at": {
            "type": "string",
            "format": "date-time"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "translated_fields": {
            "type": "array",
            "description": "Present only when `expand=translated_fields` is set and the event has language variants configured.",
            "items": {
              "type": "object"
            }
          },
          "speakers": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SessionSpeaker"
            }
          },
          "participants": {
            "type": "array",
            "description": "Sessions 2.0 participants for this subsession (see `Session.participants`).",
            "items": {
              "$ref": "#/components/schemas/SessionParticipant"
            }
          },
          "is_abstract": {
            "type": "boolean",
            "description": "Inherited from the parent session."
          },
          "composition_status": {
            "$ref": "#/components/schemas/CompositionStatus"
          },
          "format": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "name": {
                "type": "string"
              }
            }
          },
          "content": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Content"
            }
          }
        }
      },
      "SubsessionDetailed": {
        "type": "object",
        "description": "Full-parity subsession returned inside `parent.subsessions[]` when the\n`subsession_details` expand value is set on the request. The shape\nmirrors `Session` (minus the recursive `subsessions` property, since\nsubsessions cannot be nested) and adds the parent-friendly-id fields\nso callers can iterate the array and then call\n`GET /v1/event/{eventId}/sessions/{sessionId}` with each subsession\nid for the same shape at the top level.\n\n`is_abstract`, `composition_status`, and optional `composition`\n(when `expand=composition`) are inherited from the parent session.\n",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "parent_session_friendly_id": {
            "type": "string"
          },
          "parent_session_friendly_id_raw": {
            "type": "integer"
          },
          "subsession_order": {
            "type": "integer",
            "nullable": true,
            "description": "Admin-defined position among the parent session's subsessions; subsessions are returned in this order, falling back to subsession number and start time. `null` when the parent's subsessions have never been reordered."
          },
          "title": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "status": {
            "type": "string"
          },
          "custom_status_id": {
            "type": "string",
            "format": "uuid",
            "nullable": true
          },
          "custom_status": {
            "$ref": "#/components/schemas/SessionCustomStatus"
          },
          "starts_at": {
            "type": "string",
            "format": "date-time"
          },
          "ends_at": {
            "type": "string",
            "format": "date-time"
          },
          "is_public": {
            "type": "boolean"
          },
          "is_abstract": {
            "type": "boolean",
            "description": "Inherited from the parent session."
          },
          "composition_status": {
            "$ref": "#/components/schemas/CompositionStatus"
          },
          "external_url": {
            "type": "string",
            "nullable": true
          },
          "client_session_id": {
            "type": "string",
            "nullable": true
          },
          "ceu_credits": {
            "type": "number",
            "nullable": true
          },
          "capacity": {
            "type": "integer",
            "nullable": true
          },
          "translated_fields": {
            "type": "array",
            "description": "Present only when `expand=translated_fields` is set and the event has language variants configured.",
            "items": {
              "type": "object"
            }
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "custom_fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CustomFieldValue"
            }
          },
          "speakers": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SessionSpeaker"
            }
          },
          "chairpersons": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SessionSpeaker"
            }
          },
          "moderators": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SessionSpeaker"
            }
          },
          "participants": {
            "type": "array",
            "description": "Sessions 2.0 participants for this subsession (see `Session.participants`).",
            "items": {
              "$ref": "#/components/schemas/SessionParticipant"
            }
          },
          "sponsors": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Sponsor"
            }
          },
          "exhibitors": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Exhibitor"
            }
          },
          "content": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Content"
            }
          },
          "tags": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Tag"
            }
          },
          "language": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Language"
              }
            ],
            "description": "Same shape as `Session.language` when assigned; `{}` when unassigned."
          },
          "track": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Track"
              }
            ],
            "description": "Same shape as `Session.track` when assigned; `{}` when unassigned."
          },
          "level": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Level"
              }
            ],
            "description": "Same shape as `Session.level` when assigned; `{}` when unassigned."
          },
          "format": {
            "type": "object",
            "description": "Nested format includes only `id` and `name`.",
            "properties": {
              "id": {
                "type": "string"
              },
              "name": {
                "type": "string"
              }
            }
          },
          "room": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Room"
              }
            ],
            "description": "Same shape as `Session.room` when `location` is `room`; `{}` when\nlocation is external or unset.\n"
          },
          "source": {
            "type": "string"
          }
        },
        "examples": [
          {
            "id": "ff14c2e4-2abf-4610-8267-0d2935f19576",
            "friendly_id": "SESS-3370-3",
            "friendly_id_raw": 3052,
            "parent_session_friendly_id": "SESS-3370",
            "parent_session_friendly_id_raw": 3370,
            "title": "Imagining a better tomorrow",
            "status": "accepted",
            "is_public": true,
            "custom_status": null,
            "custom_fields": [
              {
                "id": "749c5737-cde4-44cc-acf6-15a6ccf74a5f",
                "name": "Co-authors",
                "type": "textarea",
                "internal_name": "co_authors",
                "value": "Mohamed Tarik, Mar...",
                "created_at": "2026-01-21T13:15:57.710Z"
              }
            ],
            "chairpersons": [],
            "moderators": [],
            "sponsors": [],
            "exhibitors": [],
            "tags": [],
            "speakers": [],
            "content": [],
            "language": {
              "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
              "event_id": 72,
              "name": "English",
              "order": 0,
              "created_at": "2025-01-01T00:00:00Z",
              "updated_at": "2025-02-01T00:00:00Z"
            },
            "track": {
              "id": "b2c3d4e5-f6a7-8901-bcde-f12345678901",
              "event_id": 72,
              "name": "Artificial Intelligence & ML",
              "color": "#329af0",
              "order": 1,
              "created_at": "2025-01-01T00:00:00Z",
              "updated_at": "2025-02-01T00:00:00Z"
            },
            "level": {
              "id": "c3d4e5f6-a7b8-9012-cdef-123456789012",
              "name": "Beginner",
              "order": 2,
              "created_at": "2025-01-01T00:00:00Z",
              "updated_at": "2025-02-01T00:00:00Z"
            },
            "format": {
              "id": "d4e5f6a7-b8c9-0123-def0-234567890123",
              "name": "Technical Programme Forum Paper"
            },
            "room": {
              "id": "e5f6a7b8-c9d0-1234-ef01-345678901234",
              "name": "Workshop Room 1",
              "order": 3,
              "capacity": 120,
              "created_at": "2025-01-01T00:00:00Z",
              "updated_at": "2025-02-01T00:00:00Z"
            },
            "source": "Manual"
          }
        ]
      },
      "SubsessionStatus": {
        "type": "object",
        "description": "A lightweight representation of a subsession's status, included as part of the parent SessionStatus response.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "friendly_id": {
            "type": "string"
          },
          "friendly_id_raw": {
            "type": "integer"
          },
          "parent_session_friendly_id": {
            "type": "string"
          },
          "parent_session_friendly_id_raw": {
            "type": "integer"
          },
          "subsession_order": {
            "type": "integer",
            "nullable": true,
            "description": "Admin-defined position among the parent session's subsessions; subsessions are returned in this order, falling back to subsession number and start time. `null` when the parent's subsessions have never been reordered."
          },
          "status": {
            "type": "string",
            "nullable": true,
            "description": "The subsession's own approval status from the database. The API does\nnot inherit the parent session's status. May be null when the\nsubsession has no explicit status set.\n"
          },
          "custom_status_id": {
            "type": "string",
            "format": "uuid",
            "nullable": true
          },
          "custom_status": {
            "$ref": "#/components/schemas/SessionCustomStatus"
          },
          "deleted_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "SessionCustomStatus": {
        "type": "object",
        "description": "A custom session status definition configured for an event.",
        "properties": {
          "id": {
            "type": "string"
          },
          "name": {
            "type": "string"
          },
          "status": {
            "type": "string",
            "description": "Approval state this custom label maps onto. Stored NOT NULL, so it\nis always present on a status created through this API.\n",
            "enum": [
              "pending",
              "accepted",
              "declined",
              "accept_queue",
              "decline_queue"
            ]
          },
          "status_name": {
            "type": "string",
            "nullable": true
          },
          "color": {
            "type": "string"
          },
          "order": {
            "type": "integer"
          },
          "is_custom": {
            "type": "boolean"
          },
          "created_at": {
            "type": "string",
            "nullable": true
          },
          "created_by_user_id": {
            "type": "integer",
            "nullable": true
          },
          "created_by_user_name": {
            "type": "string",
            "nullable": true
          }
        }
      },
      "GDPRRequest": {
        "type": "object",
        "description": "A GDPR data access or erasure request, and the record of what it did.",
        "properties": {
          "id": {
            "type": "string",
            "description": "Identifier of the stored request. Quote this when evidencing a DSAR."
          },
          "org_id": {
            "type": "string"
          },
          "request_type": {
            "type": "string",
            "enum": [
              "erasure",
              "access"
            ]
          },
          "identity_type": {
            "type": "string",
            "enum": [
              "email"
            ]
          },
          "identity_value": {
            "type": "string"
          },
          "status": {
            "type": "string",
            "enum": [
              "complete",
              "no_records_found",
              "pending"
            ],
            "description": "Outcome of the request.\n\n- `complete` — at least one record matched and was processed.\n- `no_records_found` — nothing in this organization matched the\n  email, so nothing was erased.\n- `pending` — the request is stored but has not finished\n  processing.\n"
          },
          "matching_user_exists": {
            "type": "boolean",
            "description": "True when the email matched at least one record of any kind."
          },
          "response": {
            "type": "object",
            "description": "What the request matched and what happened to it. `people`, `users_scrubbed`, `users_retained` and `counts` are present on requests processed recently and absent on older records; an absent field means \"not recorded\", not \"zero\".",
            "properties": {
              "users": {
                "type": "array",
                "description": "User accounts identified for this email.",
                "items": {
                  "type": "integer"
                }
              },
              "org_users": {
                "type": "array",
                "description": "Organization membership records removed.",
                "items": {
                  "type": "string"
                }
              },
              "event_users": {
                "type": "array",
                "description": "Event participation records removed.",
                "items": {
                  "type": "integer"
                }
              },
              "contact_records": {
                "type": "array",
                "description": "Contact records marked deleted.",
                "items": {
                  "type": "string"
                }
              },
              "people": {
                "type": "array",
                "description": "Person records whose personal data was scrubbed in place.",
                "items": {
                  "type": "string"
                }
              },
              "users_scrubbed": {
                "type": "array",
                "description": "User accounts whose personal data was de-identified.",
                "items": {
                  "type": "integer"
                }
              },
              "users_retained": {
                "type": "array",
                "description": "User accounts left intact because they still belong to another organization, with the reason recorded.",
                "items": {
                  "type": "object"
                }
              },
              "counts": {
                "type": "object",
                "description": "Per-category totals for the arrays above.",
                "properties": {
                  "org_users": {
                    "type": "integer"
                  },
                  "event_users": {
                    "type": "integer"
                  },
                  "contact_records": {
                    "type": "integer"
                  },
                  "people": {
                    "type": "integer"
                  },
                  "users_identified": {
                    "type": "integer"
                  },
                  "users_scrubbed": {
                    "type": "integer"
                  },
                  "users_retained": {
                    "type": "integer"
                  }
                }
              }
            }
          },
          "created_at": {
            "type": "string"
          },
          "updated_at": {
            "type": "string"
          }
        }
      },
      "Field": {
        "type": "object",
        "description": "A field definition (standard or custom) for an event module.",
        "properties": {
          "id": {
            "type": "string"
          },
          "internal_name": {
            "type": "string"
          },
          "public_name": {
            "type": "string"
          },
          "field_type": {
            "type": "string"
          },
          "field_source": {
            "type": "string"
          },
          "contains_pii": {
            "type": "boolean",
            "description": "Whether this field contains personally identifiable information (PII)."
          },
          "scope": {
            "type": "string"
          },
          "createdAt": {
            "type": "string"
          },
          "updatedAt": {
            "type": "string"
          }
        }
      },
      "BulkOperations": {
        "type": "object",
        "description": "Request body for bulk create/update/delete operations.\n\nOperations are applied in request order, each in its own transaction,\nand `results[i]` describes `operations[i]`. A failed operation is\nrolled back whole and does not stop the ones after it.\n",
        "required": [
          "operations"
        ],
        "properties": {
          "operations": {
            "type": "array",
            "maxItems": 100,
            "description": "Array of operations to execute (max 100).",
            "items": {
              "type": "object",
              "required": [
                "action"
              ],
              "properties": {
                "action": {
                  "type": "string",
                  "enum": [
                    "create",
                    "update",
                    "delete"
                  ],
                  "description": "The operation to perform."
                },
                "id": {
                  "type": "string",
                  "format": "uuid",
                  "description": "Entity ID. Required for `update` and `delete` actions."
                },
                "data": {
                  "type": "object",
                  "description": "Entity-specific fields. Required for `create` and `update` actions.\nSession create supports `is_abstract` (boolean, default false).\n`is_abstract` cannot be changed on update.\n\n`data` takes the same fields as the matching single-record\ncreate/update endpoint, including `custom_fields` and\n`translated_fields`. A `translated_fields` entry for a\nlanguage the event has not enabled fails that operation with\n`400` and rolls it back — it is no longer accepted and\ndiscarded.\n\n`custom_fields` is honoured on the contacts, sessions,\nexhibitors and sponsors bulk endpoints. An unknown\n`internal_name`, a value of the wrong type, or a field owned\nby an integration fails **that operation only** — the\noperations around it in the same batch still commit.\n\n**Exception — draft sessions.** `POST\n/event/{eventId}/agenda-drafts/{draftId}/sessions/bulk` does\nnot accept `custom_fields`, and neither does its\nsingle-record sibling. A draft session is a scheduling\nplacement of an existing session inside a draft agenda, not a\nrecord of its own, so it has no custom fields to write. Set\ncustom fields on the underlying session through\n`/event/{eventId}/sessions`.\n"
                }
              }
            }
          }
        }
      },
      "BulkResponse": {
        "type": "object",
        "description": "Response body for bulk operations, including per-item results.",
        "properties": {
          "batch_id": {
            "type": "string",
            "format": "uuid",
            "description": "Unique identifier for this bulk batch."
          },
          "results": {
            "type": "array",
            "description": "Per-operation results in the same order as the request.",
            "items": {
              "type": "object",
              "properties": {
                "index": {
                  "type": "integer",
                  "description": "Zero-based index of the operation in the request array."
                },
                "action": {
                  "type": "string",
                  "description": "The action that was performed (create, update, delete)."
                },
                "status": {
                  "type": "string",
                  "enum": [
                    "success",
                    "created",
                    "associated",
                    "updated",
                    "deleted",
                    "error"
                  ],
                  "description": "Whether this individual operation succeeded or failed.\n\nMost bulk endpoints report `success` or `error`. The contacts\nbulk endpoint instead names the outcome: `created`,\n`associated` (the email already existed in the organization\nand was linked to this event), `updated`, `deleted`, or\n`error`. Treat anything other than `error` as a success.\n"
                },
                "id": {
                  "type": "string",
                  "format": "uuid",
                  "description": "The ID of the created or affected entity."
                },
                "error": {
                  "description": "Error details, present only when `status` is `error`.\n\nAn object with `code` and `message` on most bulk endpoints.\nOn the contacts bulk endpoint `error` is a plain string and\nthe code is returned alongside it as `error_code`; that\ndifference is longstanding and is kept so existing callers\nreading the string keep working.\n",
                  "oneOf": [
                    {
                      "type": "object",
                      "properties": {
                        "code": {
                          "type": "string",
                          "description": "Machine-readable error code."
                        },
                        "message": {
                          "type": "string",
                          "description": "Human-readable error description."
                        },
                        "valid_options": {
                          "type": "array",
                          "items": {
                            "type": "string"
                          },
                          "description": "Present only when `code` is `TYPE_MISMATCH` on a\n`dropdown` field: every value the field accepts,\none array entry per option, in the field's option\norder. An option label can itself contain a comma\n(`\"Banana, Chocolate\"`), so read this array rather\nthan splitting the list in `message`. Absent on\nevery other error.\n"
                        }
                      },
                      "example": {
                        "code": "TYPE_MISMATCH",
                        "message": "Field 'product_type' value 'Banana' is not a valid option. Valid options: [\"1\", \"Banana, Chocolate\", \"Blue, Green, Violet\", \"10\"]",
                        "valid_options": [
                          "1",
                          "Banana, Chocolate",
                          "Blue, Green, Violet",
                          "10"
                        ]
                      }
                    },
                    {
                      "type": "string",
                      "description": "Human-readable error description (contacts bulk)."
                    }
                  ]
                },
                "error_code": {
                  "type": "string",
                  "description": "Machine-readable error code. Returned by the contacts bulk endpoint alongside the string `error`."
                }
              }
            }
          },
          "summary": {
            "type": "object",
            "description": "Aggregate counts for the batch. This page previously named the object `stats`; every bulk endpoint has always returned it as `summary`.",
            "properties": {
              "total": {
                "type": "integer",
                "description": "Total number of operations in the batch."
              },
              "succeeded": {
                "type": "integer",
                "description": "Number of operations that succeeded — every row whose `status` is not `error`, including the contacts bulk endpoint's `created`, `associated`, `updated` and `deleted`."
              },
              "failed": {
                "type": "integer",
                "description": "Number of operations that failed."
              }
            }
          }
        }
      },
      "AgendaDraft": {
        "type": "object",
        "description": "An agenda draft workspace for planning session schedule changes before committing them to the live event.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "event_id": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "status": {
            "type": "string",
            "enum": [
              "draft",
              "committed"
            ]
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "admin_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Deep link to this entity in the Sessionboard admin UI."
          }
        }
      },
      "DraftSession": {
        "type": "object",
        "description": "A session placement within an agenda draft.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "draft_id": {
            "type": "string",
            "format": "uuid"
          },
          "session_id": {
            "type": "string",
            "format": "uuid"
          },
          "starts_at": {
            "type": "string",
            "format": "date-time"
          },
          "ends_at": {
            "type": "string",
            "format": "date-time"
          },
          "room_id": {
            "type": "string",
            "format": "uuid"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "EventRule": {
        "type": "object",
        "description": "A scheduling constraint or validation rule for an event.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "event_id": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "type": {
            "type": "string"
          },
          "config": {
            "type": "object",
            "additionalProperties": true
          },
          "enabled": {
            "type": "boolean"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "Persona": {
        "type": "object",
        "description": "An evaluation persona representing an attendee type for schedule evaluation.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "event_id": {
            "type": "integer"
          },
          "name": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "config": {
            "type": "object",
            "additionalProperties": true
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "TranscriptionResponse": {
        "type": "object",
        "properties": {
          "data": {
            "$ref": "#/components/schemas/Transcription"
          }
        }
      },
      "TranscriptionListResponse": {
        "type": "object",
        "properties": {
          "data": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Transcription"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "TranscriptionElement": {
        "type": "object",
        "properties": {
          "value": {
            "type": "string"
          },
          "speaker": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "label": {
                "type": "string"
              },
              "name": {
                "type": "string",
                "nullable": true
              }
            }
          },
          "start_time": {
            "type": "number"
          },
          "end_time": {
            "type": "number"
          },
          "fragment_ids": {
            "type": "array",
            "items": {
              "type": "string",
              "format": "uuid"
            }
          }
        }
      },
      "ContentItem": {
        "type": "object",
        "description": "Typed item inside a session or event content pack.",
        "properties": {
          "id": {
            "oneOf": [
              {
                "type": "string",
                "format": "uuid"
              },
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ]
          },
          "type": {
            "type": "string",
            "enum": [
              "transcription",
              "summary",
              "insight",
              "podcast",
              "document",
              "recap"
            ]
          },
          "session_id": {
            "type": "string",
            "format": "uuid"
          },
          "text": {
            "type": "string",
            "description": "Full joined transcript (transcription items)."
          },
          "elements": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TranscriptionElement"
            }
          },
          "fragment_count": {
            "type": "integer"
          },
          "interval_sec": {
            "type": "integer",
            "nullable": true
          },
          "language_code": {
            "type": "string"
          },
          "summary_type": {
            "type": "string"
          },
          "provider": {
            "type": "string"
          },
          "content": {
            "type": "object"
          },
          "topics": {
            "type": "array",
            "items": {
              "type": "object"
            }
          },
          "insight_type": {
            "type": "string"
          },
          "name": {
            "type": "string"
          },
          "metadata": {
            "type": "object",
            "nullable": true
          },
          "status": {
            "type": "string"
          },
          "url": {
            "type": "string",
            "nullable": true
          },
          "duration_sec": {
            "type": "integer",
            "nullable": true
          },
          "generated_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          },
          "expires_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          },
          "document_type": {
            "type": "string",
            "enum": [
              "summary_pdf",
              "summary_card",
              "event_report"
            ]
          },
          "content_type": {
            "type": "string"
          },
          "scope": {
            "type": "string"
          },
          "quotes": {
            "type": "array",
            "items": {
              "type": "object"
            }
          },
          "summaries": {
            "type": "array",
            "items": {
              "type": "object"
            }
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "SessionContent": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid",
            "description": "Session id"
          },
          "event_id": {
            "type": "integer"
          },
          "title": {
            "type": "string",
            "nullable": true
          },
          "starts_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "speakers": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "id": {
                  "type": "string"
                },
                "label": {
                  "type": "string"
                },
                "name": {
                  "type": "string",
                  "nullable": true
                }
              }
            }
          },
          "has_transcription": {
            "type": "boolean"
          },
          "has_summary": {
            "type": "boolean"
          },
          "has_podcast": {
            "type": "boolean"
          },
          "items": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ContentItem"
            }
          }
        }
      },
      "SessionContentResponse": {
        "type": "object",
        "properties": {
          "data": {
            "$ref": "#/components/schemas/SessionContent"
          }
        }
      },
      "SessionContentListResponse": {
        "type": "object",
        "properties": {
          "data": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SessionContent"
            }
          },
          "pagination": {
            "type": "object",
            "properties": {
              "current_page": {
                "type": "integer"
              },
              "page_size": {
                "type": "integer"
              },
              "total_pages": {
                "type": "integer"
              },
              "total_results": {
                "type": "integer"
              }
            }
          }
        }
      },
      "EventContent": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Event id"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "items": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ContentItem"
            }
          }
        }
      },
      "EventContentResponse": {
        "type": "object",
        "properties": {
          "data": {
            "$ref": "#/components/schemas/EventContent"
          }
        }
      },
      "ContentItemResponse": {
        "type": "object",
        "properties": {
          "data": {
            "$ref": "#/components/schemas/ContentItem"
          }
        }
      },
      "Transcription": {
        "type": "object",
        "description": "Polymorphic transcription artifact. Fields vary by type.",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "type": {
            "type": "string",
            "enum": [
              "fragment",
              "summary",
              "insight",
              "translation"
            ]
          },
          "session_id": {
            "type": "string",
            "format": "uuid"
          },
          "transcription": {
            "type": "string"
          },
          "speaker": {
            "type": "string"
          },
          "is_partial": {
            "type": "boolean"
          },
          "provider": {
            "type": "string"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "TranscriptionCreateRequest": {
        "type": "object",
        "required": [
          "type"
        ],
        "properties": {
          "type": {
            "type": "string",
            "enum": [
              "fragment",
              "summary",
              "insight",
              "translation"
            ]
          },
          "transcription": {
            "type": "string"
          }
        }
      },
      "Recording": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "type": {
            "type": "string",
            "example": "recording"
          },
          "session_id": {
            "type": "string",
            "format": "uuid"
          },
          "s3_bucket": {
            "type": "string"
          },
          "s3_key": {
            "type": "string",
            "description": "After complete, non-PCM uploads are stored as `.pcm` keys."
          },
          "encoding": {
            "type": "string",
            "example": "linear16"
          },
          "sample_rate": {
            "type": "integer",
            "example": 16000
          },
          "channels": {
            "type": "integer",
            "example": 1
          },
          "status": {
            "type": "string",
            "enum": [
              "recording",
              "completed"
            ]
          },
          "duration_seconds": {
            "type": "number"
          },
          "file_size_bytes": {
            "type": "integer"
          },
          "started_at": {
            "type": "string",
            "format": "date-time"
          },
          "completed_at": {
            "type": "string",
            "format": "date-time"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          },
          "mp3_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "6-hour presigned HTTPS URL for an MP3 sibling of the original PCM take. Null while the recording is in progress or if transcode has not succeeded yet. Download and store this file — do not hotlink it as a permanent CDN URL. Session PDFs and user-uploaded files stay on `/content` and `/files`.\n"
          },
          "mp3_expires_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true,
            "description": "When `mp3_url` stops working. Request the recording again to refresh the URL."
          }
        }
      },
      "RecordingResponse": {
        "type": "object",
        "properties": {
          "data": {
            "$ref": "#/components/schemas/Recording"
          }
        }
      },
      "RecordingCreateResponse": {
        "type": "object",
        "properties": {
          "data": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Recording"
              },
              {
                "type": "object",
                "properties": {
                  "upload": {
                    "type": "object",
                    "properties": {
                      "url": {
                        "type": "string"
                      },
                      "method": {
                        "type": "string",
                        "example": "PUT"
                      },
                      "headers": {
                        "type": "object",
                        "properties": {
                          "Content-Type": {
                            "type": "string"
                          }
                        }
                      }
                    }
                  }
                }
              }
            ]
          }
        }
      },
      "MediaItem": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "type": {
            "type": "string",
            "example": "media_item"
          },
          "title": {
            "type": "string"
          },
          "platform": {
            "type": "string"
          },
          "kind": {
            "type": "string"
          },
          "event_id": {
            "type": "integer"
          },
          "session_id": {
            "type": "string",
            "format": "uuid"
          },
          "media_s3_key": {
            "type": "string"
          },
          "transcript_status": {
            "type": "string",
            "enum": [
              "queued",
              "processing",
              "ready",
              "failed"
            ]
          },
          "duration_seconds": {
            "type": "number"
          },
          "created_at": {
            "type": "string",
            "format": "date-time"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "MediaItemResponse": {
        "type": "object",
        "properties": {
          "data": {
            "$ref": "#/components/schemas/MediaItem"
          }
        }
      },
      "SessionFileCreateRequest": {
        "type": "object",
        "required": [
          "filename",
          "size_bytes"
        ],
        "properties": {
          "filename": {
            "type": "string",
            "description": "Original filename including extension (e.g. `slides.pptx`, `handout.pdf`).",
            "example": "keynote-slides.pptx"
          },
          "size_bytes": {
            "type": "integer",
            "minimum": 1,
            "maximum": 524288000,
            "description": "Exact file size in bytes. Maximum 500 MB (524288000) for direct-to-storage upload. Use `POST .../files/upload` for files up to 50 MB without specifying size."
          },
          "content_type": {
            "type": "string",
            "description": "MIME type. Optional; inferred from the filename extension when omitted.",
            "example": "application/vnd.openxmlformats-officedocument.presentationml.presentation"
          },
          "mimetype": {
            "type": "string",
            "description": "Alias for `content_type`."
          },
          "title": {
            "type": "string",
            "description": "Display title. Defaults to `filename`."
          },
          "assigned_participant_id": {
            "type": "string",
            "format": "uuid",
            "nullable": true,
            "description": "Contact UUID of a session participant to assign this file to."
          },
          "content_slot_id": {
            "type": "string",
            "format": "uuid",
            "nullable": true,
            "description": "The [upload slot](/api-reference/session-files/list-upload-slots)\nthis file answers. Optional — API callers act as the organization,\nso no slot deadline applies and a file may be attached without a\nslot. When set, the slot must be active, apply to the session\n(`GET .../content-slots?session_id=`), accept the file's declared\ntype and have room under its `max_files`; otherwise `400` names the\nslot. The file's `type` is derived from the slot's `content_type`.\nIgnored on events that still use a single file request.\n"
          }
        }
      },
      "SessionFileUpdateRequest": {
        "type": "object",
        "properties": {
          "title": {
            "type": "string",
            "nullable": true
          },
          "assigned_participant_id": {
            "type": "string",
            "format": "uuid",
            "nullable": true
          }
        }
      },
      "SessionFileResponse": {
        "type": "object",
        "properties": {
          "data": {
            "$ref": "#/components/schemas/Content"
          }
        }
      },
      "SessionFileListResponse": {
        "type": "object",
        "properties": {
          "data": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Content"
            }
          }
        }
      },
      "SessionFileCreateResponse": {
        "type": "object",
        "properties": {
          "data": {
            "allOf": [
              {
                "$ref": "#/components/schemas/Content"
              },
              {
                "type": "object",
                "properties": {
                  "upload": {
                    "type": "object",
                    "properties": {
                      "url": {
                        "type": "string",
                        "format": "uri",
                        "description": "Presigned S3 URL — PUT the file bytes here."
                      },
                      "method": {
                        "type": "string",
                        "example": "PUT"
                      },
                      "headers": {
                        "type": "object",
                        "properties": {
                          "Content-Type": {
                            "type": "string"
                          }
                        }
                      }
                    }
                  }
                }
              }
            ]
          }
        }
      }
    }
  }
}
