{
  "openapi": "3.1.0",
  "info": {
    "title": "100Hires API",
    "version": "2.0.0",
    "description": "## Introduction to the 100Hires ATS API\nThe 100Hires ATS API (v2) helps you automate recruiting workflows end-to-end: candidates, applications, jobs, forms, notes, and partner-company operations.\nAll endpoints return JSON and use bearer authentication.\n\n## OpenAPI Spec\nThe 100Hires ATS API follows the OpenAPI 3.x specification. Download the machine-readable spec for use in MCP servers, Cursor, Claude Code, or any OpenAPI tooling:\n\n`GET https://api.100hires.com/v2/openapi.json`\n\n## Authentication\nSend API token in the `Authorization` header for every request:\n\n`Authorization: Bearer <token>`\n\nEach API key is tied to a specific **user + company** pair.\nIf the same user belongs to multiple companies, they need a separate key for each company.\nAll actions performed through the API are attributed to the key owner.\n\nYou can generate or view your API key at https://app.100hires.com/settings/integrations\n\n### API Key Verification\nAPI keys for **unverified companies** are created in a disabled state and will return `401 Unauthorized` until the company passes verification.\n\nOnce your company is verified, API keys start working automatically — no action required.\n\nIf your key returns `401` and you believe your company should be verified, contact **support@100hires.com**.\n\n## Rate Limits\nNew API keys are subject to a hard rate limit of **100 requests per 10 minutes** per key.\nRequests over the limit receive a `429 Too Many Requests` response.\n\n### Rate limit headers\nUnapproved keys include these headers on every response:\n\n| Header | Description |\n|--------|-------------|\n| `X-RateLimit-Limit` | Maximum requests allowed in the current window |\n| `X-RateLimit-Remaining` | Requests remaining in the current window |\n| `X-RateLimit-Reset` | Unix timestamp (seconds) when the window resets |\n\n### Handling 429 responses\nWhen you receive a `429` response, wait until `X-RateLimit-Reset` before retrying.\nDo not retry immediately — repeated 429s may extend the cooldown.\n\nTo remove rate limits for your integration, contact **support@100hires.com** with your use case.\n\n## Content-Type\nAll request bodies **must** use `Content-Type: application/json`.\nSending `application/x-www-form-urlencoded`, `multipart/form-data`, or any other content type\nwill result in a `415 Unsupported Media Type` error.\n\n## Responses and Errors\nStandard HTTP status codes are used (`2xx`, `4xx`, `5xx`).\nValidation errors return `success: false` with field-level `errors`.\nException-based errors return `name`, `message`, `code`, and optional `status`.\n\n## Pagination\nList endpoints use `page` (1-based) and `size` (1-100, default 20).\nPaginated responses follow:\n`{ \"<resource>\": [...], \"pagination\": { \"page_size\", \"page_count\", \"page\", \"total_count\" } }`.\n\n## Lists\nList routes are optimized for synchronization and operational dashboards.\nMost list endpoints support tenant scoping through optional `company_id` (when allowed by API key context).\n\n## Confidential Data\nSome candidate profile values can be masked by account-level pricing/access rules.\nIntegrations should not assume all profile fields are always fully visible.\n\n## Customizing the Response\nUse endpoint filters (`status`, `job_id`, timestamps, taxonomy IDs, etc.) to minimize payload size and improve sync efficiency.\nBuild incremental sync flows around timestamp filters where available.\n\n## Supported File Formats\nFile uploads use base64 payloads with metadata:\n`data`, `file_name`, `mime_type` (and optionally `size`).\nThis format is used for candidate files, resumes, attachments, and logos.\n\n## Webhooks\nWebhook subscriptions can be managed per job and per company.\n\n### Set up\nUse webhook endpoints to register destination URLs for events in your integration.\n\n### Securing webhooks\nEvery delivery is signed with the `x-hires-signature-v2` header: `base64(HMAC_SHA256(rawBody, secret))`,\ncomputed over the **raw request body** with the webhook's signing secret (returned once when you create or\nrotate the webhook). Verify it before trusting a request and reject anything that does not match.\n\nDuring a secret rotation, `x-hires-signature-v2` may carry **multiple** space-separated signatures (one per\ncurrently-valid secret). Treat the header as a space-separated list and accept the request if any entry matches\na secret you hold.\n\nVerification example for `x-hires-signature-v2` (Node.js):\n```js\nconst crypto = require('crypto');\nconst expected = crypto.createHmac('sha256', signingSecret).update(rawBody).digest('base64');\nconst provided = (req.headers['x-hires-signature-v2'] || '').split(' ');\nconst verified = provided.includes(expected);\n```\n\n#### Signing secrets and rotation\nEach webhook owns its own signing secret, independent of your API key. The secret is returned **once** as\n`signing_secret` when you create the webhook (`POST /jobs/{id}/webhooks`, `POST /companies/{id}/webhooks`) — store\nit securely, it is never shown again. To rotate with zero downtime, call\n`POST /jobs/{id}/webhooks/{webhook_id}/rotate-secret` (or the company equivalent): the previous secret stays valid\nfor a grace window while both old and new signatures are sent, so you can switch the secret on your side without\ndropping any deliveries.\n\n### Receiving webhooks\nAlways respond quickly with `2xx`, then process asynchronously to avoid retries/timeouts.\n\n### Event payloads\nOn each new application, 100hires sends a `POST` to your registered URL with a JSON body describing the\napplication. Verify the signature (see \"Securing webhooks\") before processing, and parse defensively — fields\nmay be `null` and new fields may be added over time.\n\nWebhooks registered through this API (v2) receive the payload below. (Webhooks created via the legacy v1 API\nreceive a different, legacy payload — register through v2 to receive this richer shape.)\n\nExample delivery payload:\n```json\n{\n  \"id\": 845112,\n  \"candidate_id\": 390217,\n  \"job_id\": 4821,\n  \"job_alias\": \"senior-backend-engineer\",\n  \"internal_job_id\": 12,\n  \"company_id\": 1007,\n  \"stage\": { \"id\": 3, \"name\": \"Applied\" },\n  \"status\": \"active\",\n  \"is_disqualified\": false,\n  \"url_backoffice\": \"https://app.100hires.com/candidate/default/view?candidate=390217&application=845112\",\n  \"cv\": {\n    \"url\": \"https://api.100hires.com/v2/files/9f1c2e7a-3b4c-4d5e-8f90-1a2b3c4d5e6f/download\",\n    \"uuid\": \"9f1c2e7a-3b4c-4d5e-8f90-1a2b3c4d5e6f\",\n    \"relative_time\": \"2 hours ago\",\n    \"file\": {\n      \"is_image\": false,\n      \"orig_file_name\": \"jane_doe_resume.pdf\",\n      \"file_ext\": \"pdf\",\n      \"file_type\": \"application/pdf\",\n      \"readable_size\": \"100kB\"\n    },\n    \"text\": \"Jane Doe — Senior Backend Engineer\\n8 years building distributed systems…\"\n  },\n  \"rejected_at\": null,\n  \"rejection_reason\": null,\n  \"hired_at\": null,\n  \"hiring_team\": null,\n  \"custom_fields\": null,\n  \"created_at\": 1781434800,\n  \"updated_at\": 1781434800,\n  \"last_message_at\": null,\n  \"days_since_last_message\": null,\n  \"ai_score\": null,\n  \"ai_recommendation\": null,\n  \"ai_scoring_updated_at\": null,\n  \"candidate\": {\n    \"id\": 390217,\n    \"alias\": \"jane-doe\",\n    \"company_id\": 1007,\n    \"first_name\": \"Jane\",\n    \"last_name\": \"Doe\",\n    \"emails\": [\"jane.doe@example.com\"],\n    \"phones\": [\"+1 555 123 4567\"],\n    \"source\": { \"id\": 5, \"name\": \"LinkedIn\" },\n    \"origin\": { \"id\": 2, \"name\": \"Career site\" },\n    \"profile\": [\n      { \"question_id\": 1, \"question_text\": \"First name\", \"value\": \"Jane\" },\n      { \"question_id\": 3, \"question_text\": \"Email\", \"value\": \"jane.doe@example.com\" }\n    ]\n  }\n}\n```\n\nField reference:\n- `id` — application id. `candidate_id`, `job_id`, `company_id` — related entity ids.\n- `job_alias` — the job's URL slug; `internal_job_id` — human-facing job number (present when set).\n- `stage` — current pipeline stage `{ id, name }`, or `null`. `status` — `active`, `rejected`, or `hired`.\n- `is_disqualified` — `true` when the application has been rejected/disqualified.\n- `url_backoffice` — deep link to the application in the 100hires back office.\n- `cv` — résumé `{ url, uuid, relative_time, file { … }, text }`, or `null` when there is no résumé. `text` is the\n  parsed résumé content (can be large).\n- `rejected_at` / `hired_at` — Unix timestamps, or `null`. `rejection_reason` — array of `{ id, name }`, or `null`.\n- `created_at` / `updated_at` / `last_message_at` — Unix timestamps (seconds; nullable where noted).\n- `ai_score` / `ai_recommendation` / `ai_scoring_updated_at` — AI scoring fields, `null` when not scored.\n- `candidate` — the full applicant object (name, emails, phones, source/origin, `profile` answers) —\n  same shape as `GET /candidates/{id}`. Use it to create the lead on your side.\n\nParse payloads defensively and keep backward compatibility in your consumer.\n\n### Event configuration\nEvent availability can vary by endpoint scope (job/company) and account configuration.\n\n### Responding to webhooks\nUse idempotent handlers so duplicate deliveries do not create duplicate side effects.\n\n### Delivery history\nLog incoming webhook IDs and processing results for replay, debugging, and audit.\n\n## Common Workflows\n\n### Search and review a candidate\nUsing the 100Hires ATS API you can search for candidates and review their full profile, application history, and communication timeline.\n\n1. `GET /candidates?q=John` — find candidate by name or email\n2. `GET /candidates/{id}` — full profile with application history\n3. `GET /candidates/{id}/activities` — timeline (notes, calls, AI scoring)\n4. `GET /candidates/{id}/messages` — email conversation history\n\n### Manage hiring pipeline\nUsing the 100Hires ATS API you can manage your hiring pipeline by filtering candidates by stage, advancing or rejecting applications, and performing bulk stage transitions.\n\n1. `GET /applications?job_id=123&stage_id=456` — candidates at a specific stage\n2. `POST /applications/{id}/move` with `{\"stage_id\": 789}` — advance candidate\n3. `POST /applications/{id}/reject` — reject with optional reason\n4. `POST /applications/batch/move` — bulk stage transition\n\n### Publish a job\nUsing the 100Hires ATS API you can create job drafts, publish them, and distribute to multiple job boards in one request.\n\n1. `POST /jobs` — create job draft\n2. `POST /jobs/{id}/status` with `{\"status\": \"Public\"}` — publish\n3. `GET /jobs/{id}/job-boards` — available boards\n4. `POST /jobs/batch-job-boards` — publish to multiple boards\n\n### Schedule an interview\nUsing the 100Hires ATS API you can check interviewer availability and schedule interviews for application candidates.\n\n1. `GET /interviews?interviewer_user_id=5` — check interviewer availability\n2. `POST /applications/{id}/interviews` — create interview for application\n\n### Evaluate a candidate\nUsing the 100Hires ATS API you can retrieve evaluation forms and review candidate scores and feedback.\n\n1. `GET /applications/{id}/evaluation-forms` — list filled evaluations\n2. `GET /evaluation-forms/{id}` — detailed form with answers and scores\n\n### Send an email\nUsing the 100Hires ATS API you can send emails to candidates, schedule bulk messages, and cancel pending deliveries.\n\n1. `GET /candidates/{id}/messages` — check conversation history\n2. *(Optional)* `GET /users/{user_id}/mail-accounts` — find `mail_account_id` to send from a specific user's mailbox\n3. `POST /candidates/{id}/messages` — schedule email (use `from_account_id` to send from a specific mailbox; 15-min cancel window by default)\n4. `POST /messages/batch/create` — schedule up to 100 emails in one request (each with its own `candidate_id`)\n5. `DELETE /messages/{id}` — cancel before send\n\n### Monitor outreach by mail account\nUsing the 100Hires ATS API you can monitor outreach by tracking messages sent from specific mail accounts.\n\n1. `GET /companies/mail-accounts` or `GET /users/{user_id}/mail-accounts` — find `mail_account_id`\n2. `GET /messages?from_account_id={id}` — list all messages sent/scheduled from that account\n3. Filter by `status=scheduled` to see pending queue, `status=sent` for delivery history\n4. Use `date_from` / `date_to` (unix timestamps) to narrow the time range\n\n### Send an email from another team member's mailbox\nUsing the 100Hires ATS API you can send emails from any team member's connected mailbox.\n\n1. `GET /users` — find the `user_id` of the team member\n2. `GET /users/{user_id}/mail-accounts` — get their `mail_account_id`\n3. `POST /candidates/{id}/messages` with `from_account_id` — send from their mailbox\n\n### Tag and organize candidates\nUsing the 100Hires ATS API you can tag candidates individually or in bulk for better organization.\n\n1. `POST /candidates/{id}/tags` with `[\"senior\", \"remote\"]` — add tags\n2. `POST /candidates/batch/tags` — bulk add tags\n3. `DELETE /candidates/batch/tags` — bulk remove tags\n\n## IDs, aliases, and building UI links\n\nEvery candidate and job has a short **alias** (e.g. `dtGeby2`, `79SZHfT`) — the same string used in 100Hires UI URLs.\n\n### Using aliases in API requests\n\nFor **candidates** and **jobs**, the `{id}` path parameter accepts either a numeric ID or an alias:\n- `GET /candidates/42` and `GET /candidates/dtGeby2` both return the same candidate.\n- `GET /jobs/1` and `GET /jobs/79SZHfT` both return the same job.\n- This also works for their sub-resources: `GET /candidates/dtGeby2/activities`, `PUT /jobs/79SZHfT`, etc.\n- All other endpoints (applications, notes, interviews, etc.) accept only numeric IDs.\n\n### Alias fields in responses\n\n- `GET /candidates` and `GET /candidates/{id}` return `alias` field for each candidate.\n- `GET /jobs` and `GET /jobs/{id}` return `alias` field for each job.\n- `GET /applications` and `GET /applications/{id}` return `job_alias` field alongside `job_id`.\n\n### Building UI links from API data\n\nUse aliases to construct direct links to 100Hires UI:\n- Candidate profile: `https://app.100hires.com/candidate/{candidate_alias}`\n- Candidate on a specific job pipeline: `https://app.100hires.com/candidate/{candidate_alias}/{job_alias}`\n- Job pipeline: `https://app.100hires.com/job/{job_alias}/candidates/pipeline`\n\nThis is useful for generating clickable links in reports, sales pipeline audits, and automation outputs.\n\n## Error handling\n\nAll errors are wrapped in an `error` object. The format is consistent across all endpoints:\n\n```json\n{\"error\": {\"name\": \"Not Found\", \"message\": \"Candidate not found\", \"code\": 0, \"status\": 404}}\n```\n\nValidation errors include field-level details in `validation_errors`:\n\n```json\n{\"error\": {\"name\": \"Validation Error\", \"message\": \"\", \"code\": 0, \"status\": 400, \"validation_errors\": {\"email\": \"Email cannot be blank.\"}}}\n```\n\n| Status | Name | When |\n|--------|------|------|\n| 400 | Bad Request | Invalid request parameters |\n| 400 | Validation Error | Model validation failed (includes `validation_errors`) |\n| 401 | Unauthorized | Missing or invalid API key |\n| 403 | Forbidden | No permission for this resource |\n| 404 | Not Found | Resource does not exist |\n| 415 | Unsupported Media Type | Content-Type is not application/json |\n| 429 | Too Many Requests | Rate limit exceeded |\n"
  },
  "servers": [
    {
      "url": "https://api.100hires.com/v2",
      "description": "Production API endpoint"
    }
  ],
  "security": [
    {
      "BearerAuth": [

      ]
    }
  ],
  "tags": [
    {
      "name": "Candidates",
      "description": "Candidate profile lifecycle: search, deduplication, files, tags, and activity timeline."
    },
    {
      "name": "Applications",
      "description": "Application lifecycle: creation, stage movement, rejection/hire actions, and attachments."
    },
    {
      "name": "Interviews",
      "description": "Interview scheduling: list, view, and create interviews linked to applications and candidates."
    },
    {
      "name": "Jobs",
      "description": "Job lifecycle and publishing: CRUD, status transitions, hiring team, boards, and webhooks."
    },
    {
      "name": "Companies",
      "description": "Partner multi-tenant company management, including restore and webhook registration."
    },
    {
      "name": "Evaluations",
      "description": "Filled evaluation forms with scores and answers submitted by interviewers for applications."
    },
    {
      "name": "Notes",
      "description": "Discussion notes linked to candidates for recruiter collaboration and context sharing."
    },
    {
      "name": "Messages",
      "description": "Candidate communication history and scheduler-backed email delivery endpoints."
    },
    {
      "name": "Notification Messages",
      "description": "Manage notification emails (rejection, interview reminders, etc.) auto-created by the system: view, edit, cancel, or bulk-cancel before delivery."
    },
    {
      "name": "Forms",
      "description": "Application forms and per-question required/optional/hidden status control."
    },
    {
      "name": "Email Templates",
      "description": "Email template CRUD for automation, nurture campaigns, and manual outreach."
    },
    {
      "name": "Template Placeholders",
      "description": "Discover and prepare dynamic placeholders (e.g. first name, job title) for use in email templates. Placeholders are inserted as HTML `<tag>` elements returned by `POST /template-placeholders/prepare`; raw `{{…}}` tokens are not substituted."
    },
    {
      "name": "Nurture Campaigns",
      "description": "Nurture campaign CRUD with multi-step sequences (email, SMS, voicemail, move stage, assign tag/task)."
    },
    {
      "name": "Questions",
      "description": "Reusable question catalog and supported question type discovery."
    },
    {
      "name": "Users",
      "description": "Company user directory and role-aware identity lookups."
    },
    {
      "name": "Taxonomy",
      "description": "Reference dictionaries used across jobs, candidates, and workflow orchestration."
    },
    {
      "name": "Billing",
      "description": "Pricing state checks to gate paid-only API capabilities."
    },
    {
      "name": "Attachments",
      "description": "Download attachment bytes by category and UUID.\n\nURLs in this format are returned in other API responses — resumes (`/candidates/{id}/resume`), candidate files (`/candidates/{id}/files`), application attachments (`/applications/{id}/attachments`), message attachments (inside `/candidates/{id}/messages`), call recordings (inside activity events).\n\nAuthentication is the same Bearer token used for the rest of the API. The response is a binary stream with `Content-Type` from the stored MIME type, `Content-Length`, and `Content-Disposition: attachment; filename=\"...\"` (original filename).\n"
    },
    {
      "name": "Feedback",
      "description": "Structured API feedback endpoint for agents and integrations to report issues and suggest improvements."
    },
    {
      "name": "Career Site",
      "description": "Public API for career site integrations. Authenticates by company slug instead of Bearer token.\n\nPass the company slug via the `X-Company-Slug` header (or `company_slug` query param).\nNo user context is required — these endpoints are public.\n"
    }
  ],
  "x-tagGroups": [
    {
      "name": "Recruiting Operations",
      "tags": [
        "Candidates",
        "Applications",
        "Interviews",
        "Jobs",
        "Evaluations",
        "Notes",
        "Messages",
        "Notification Messages",
        "Forms",
        "Questions",
        "Email Templates",
        "Nurture Campaigns",
        "Template Placeholders",
        "Users",
        "Attachments"
      ]
    },
    {
      "name": "Organization and Settings",
      "tags": [
        "Companies",
        "Taxonomy",
        "Billing",
        "Feedback"
      ]
    },
    {
      "name": "Career Site (Public)",
      "tags": [
        "Career Site"
      ]
    }
  ],
  "paths": {
    "/candidates": {
      "get": {
        "tags": [
          "Candidates"
        ],
        "summary": "List candidates",
        "operationId": "listCandidates",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "name": "job_id",
            "in": "query",
            "schema": {
              "type": "integer"
            },
            "description": "Filter candidates by job ID."
          },
          {
            "name": "stage_id",
            "in": "query",
            "schema": {
              "type": "integer"
            },
            "description": "Filter candidates by pipeline stage ID. Best used together with job_id."
          },
          {
            "name": "email",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Exact candidate email filter."
          },
          {
            "name": "q",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Plain-text candidate search by name or email. Supports partial matches. If combined with other filters, all filters must match."
          },
          {
            "name": "full_name",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Candidate full-name filter. If combined with email or q, all supplied filters must match."
          },
          {
            "name": "linkedin",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Search by LinkedIn profile URL or alias. Accepts full URL (https://linkedin.com/in/johndoe) or just the alias (johndoe). Server normalizes before matching."
          },
          {
            "name": "created_after",
            "in": "query",
            "description": "Return only candidates created at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "updated_after",
            "in": "query",
            "description": "Return only candidates updated at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds. Use for incremental sync.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "$ref": "#/components/parameters/CandidateIncludeQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Candidate list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CandidateListResponse"
                },
                "example": {
                  "candidates": [
                    {
                      "id": 12345,
                      "company_id": 1,
                      "first_name": "John",
                      "last_name": "Doe",
                      "emails": [
                        "john.doe@example.com"
                      ],
                      "phones": [
                        "+1 5551234567"
                      ],
                      "source": {
                        "id": 1,
                        "name": "LinkedIn"
                      },
                      "origin": {
                        "id": 1,
                        "name": "Direct"
                      },
                      "profile": [
                        {
                          "question_id": 1,
                          "question_text": "Email",
                          "value": [
                            "john.doe@example.com"
                          ]
                        },
                        {
                          "question_id": 5,
                          "question_text": "Current job title",
                          "value": "Senior Developer"
                        }
                      ],
                      "ip": null,
                      "created_at": 1711036800,
                      "updated_at": 1711036800,
                      "last_message_at": null,
                      "days_since_last_message": null
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns a paginated candidate list for one company or all companies accessible by the API key. Use filters for deduplication, exports, and incremental synchronization jobs."
      },
      "post": {
        "tags": [
          "Candidates"
        ],
        "summary": "Create candidate",
        "operationId": "createCandidate",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CandidateWriteRequest"
              },
              "example": {
                "first_name": "Alice",
                "last_name": "Johnson",
                "email": "alice.johnson@example.com",
                "job_id": 123,
                "stage_id": 456,
                "profile": {
                  "Current job title": "Senior Engineer",
                  "Current company": "Acme Corp"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created candidate",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Candidate"
                },
                "example": {
                  "id": 12346,
                  "alias": "kFm9Qr3",
                  "url_backoffice": "https://app.100hires.com/candidate/kFm9Qr3",
                  "company_id": 1,
                  "first_name": "Alice",
                  "last_name": "Johnson",
                  "emails": [
                    "alice.johnson@example.com"
                  ],
                  "phones": [

                  ],
                  "source": {
                    "id": 2,
                    "name": "Referral"
                  },
                  "origin": {
                    "id": 1,
                    "name": "Direct"
                  },
                  "profile": [
                    {
                      "question_id": 1,
                      "question_text": "Email",
                      "value": [
                        "alice.johnson@example.com"
                      ]
                    },
                    {
                      "question_id": 5,
                      "question_text": "Current job title",
                      "value": "Senior Engineer"
                    },
                    {
                      "question_id": 6,
                      "question_text": "Current company",
                      "value": "Acme Corp"
                    }
                  ],
                  "ip": null,
                  "applications": [
                    {
                      "id": 503,
                      "job": {
                        "id": 123,
                        "title": "Backend Engineer"
                      },
                      "stage": {
                        "id": 456,
                        "name": "Applied"
                      }
                    }
                  ],
                  "created_at": 1711036800,
                  "updated_at": 1711036800,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Creates a candidate profile and optionally links it to a job/stage on creation. Common entrypoint for imports, inbound forms, and enrichment workflows."
      }
    },
    "/candidates/{id}": {
      "get": {
        "tags": [
          "Candidates"
        ],
        "summary": "Get candidate",
        "operationId": "getCandidate",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Candidate",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Candidate"
                },
                "example": {
                  "id": 12345,
                  "alias": "dtGeby2",
                  "url_backoffice": "https://app.100hires.com/candidate/dtGeby2",
                  "company_id": 1,
                  "first_name": "John",
                  "last_name": "Doe",
                  "emails": [
                    "john.doe@example.com"
                  ],
                  "phones": [
                    "+1 5551234567"
                  ],
                  "source": {
                    "id": 1,
                    "name": "LinkedIn"
                  },
                  "origin": {
                    "id": 1,
                    "name": "Direct"
                  },
                  "profile": [
                    {
                      "question_id": 1,
                      "question_text": "Email",
                      "value": [
                        "john.doe@example.com"
                      ]
                    },
                    {
                      "question_id": 5,
                      "question_text": "Current job title",
                      "value": "Senior Developer"
                    }
                  ],
                  "ip": null,
                  "applications": [
                    {
                      "id": 501,
                      "job": {
                        "id": 123,
                        "title": "Backend Engineer"
                      },
                      "stage": {
                        "id": 10,
                        "name": "Interview"
                      }
                    }
                  ],
                  "created_at": 1711036800,
                  "updated_at": 1711036800,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns full candidate data including application summaries."
      },
      "put": {
        "tags": [
          "Candidates"
        ],
        "summary": "Update candidate",
        "operationId": "updateCandidate",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CandidateWriteRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated candidate",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Candidate"
                },
                "example": {
                  "id": 12345,
                  "alias": "dtGeby2",
                  "url_backoffice": "https://app.100hires.com/candidate/dtGeby2",
                  "company_id": 1,
                  "first_name": "Alice",
                  "last_name": "Johnson",
                  "emails": [
                    "alice.johnson@example.com"
                  ],
                  "phones": [
                    "+1 5559876543"
                  ],
                  "source": {
                    "id": 2,
                    "name": "Referral"
                  },
                  "origin": {
                    "id": 1,
                    "name": "Direct"
                  },
                  "profile": [
                    {
                      "question_id": 1,
                      "question_text": "Email",
                      "value": [
                        "alice.johnson@example.com"
                      ]
                    },
                    {
                      "question_id": 5,
                      "question_text": "Current job title",
                      "value": "Senior Engineer"
                    }
                  ],
                  "ip": null,
                  "applications": [
                    {
                      "id": 502,
                      "job": {
                        "id": 123,
                        "title": "Backend Engineer"
                      },
                      "stage": {
                        "id": 11,
                        "name": "Offer"
                      }
                    }
                  ],
                  "created_at": 1711036800,
                  "updated_at": 1711123200,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Updates candidate fields, profile answers, and optional CV payload. Designed for bi-directional sync from ATS, CRM, sourcing, or enrichment tools."
      },
      "delete": {
        "tags": [
          "Candidates"
        ],
        "summary": "Delete candidate",
        "operationId": "deleteCandidate",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes a candidate. Use this to keep external systems aligned with candidate lifecycle policies."
      }
    },
    "/candidates/{id}/tags": {
      "get": {
        "tags": [
          "Candidates"
        ],
        "summary": "List candidate tags",
        "operationId": "listCandidateTags",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Candidate tags",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TagListResponse"
                },
                "example": {
                  "tags": [
                    "Senior",
                    "Engineering",
                    "Remote"
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 3
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns all tags assigned to a candidate. Useful for segmentation sync and audience-based automations."
      },
      "post": {
        "tags": [
          "Candidates"
        ],
        "summary": "Attach tags to candidate",
        "operationId": "addCandidateTags",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/TagWriteRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated candidate tags",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TagListResponse"
                },
                "example": {
                  "tags": [
                    "Senior",
                    "Engineering",
                    "Remote",
                    "Urgent"
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 4
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Adds one or more tags to a candidate in a single request. Typical use case: campaign tagging, qualification labels, and source attribution."
      }
    },
    "/candidates/{id}/tags/{tag}": {
      "delete": {
        "tags": [
          "Candidates"
        ],
        "summary": "Delete candidate tag",
        "operationId": "deleteCandidateTag",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          },
          {
            "$ref": "#/components/parameters/TagPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Removes a specific tag from a candidate. Use when external logic recalculates segmentation or lifecycle labels."
      }
    },
    "/candidates/{id}/files": {
      "get": {
        "tags": [
          "Candidates"
        ],
        "summary": "List candidate files",
        "operationId": "listCandidateFiles",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Candidate files",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CandidateFilesResponse"
                },
                "example": {
                  "files": [
                    {
                      "uuid": "7a3c0d5f-8b4e-4a9f-9e1c-2a3b4c5d6e7f",
                      "url": "https://api.100hires.com/v2/attachments/candidate/7a3c0d5f-8b4e-4a9f-9e1c-2a3b4c5d6e7f/john_doe_resume.pdf",
                      "relative_time": "2 days ago",
                      "file": {
                        "is_image": false,
                        "orig_file_name": "john_doe_resume.pdf",
                        "file_ext": "pdf",
                        "file_type": "application/pdf",
                        "readable_size": "240 KB"
                      }
                    },
                    {
                      "uuid": "9c2b4d6e-1a8f-4d7c-8b5e-3c9a0d2e4f6b",
                      "url": "https://api.100hires.com/v2/attachments/candidate/9c2b4d6e-1a8f-4d7c-8b5e-3c9a0d2e4f6b/portfolio.pdf",
                      "relative_time": "1 day ago",
                      "file": {
                        "is_image": false,
                        "orig_file_name": "portfolio.pdf",
                        "file_ext": "pdf",
                        "file_type": "application/pdf",
                        "readable_size": "1 MB"
                      }
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Lists candidate attachments and metadata (resume/other files). Use for document sync, compliance exports, and recruiter tooling."
      },
      "post": {
        "tags": [
          "Candidates"
        ],
        "summary": "Upload candidate file",
        "operationId": "uploadCandidateFile",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CandidateFileUploadRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Uploaded file",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CandidateFile"
                },
                "example": {
                  "uuid": "4e8a2f1b-5c7d-4f9e-8a3b-6d1e2f3a4b5c",
                  "url": "https://api.100hires.com/v2/attachments/candidate/4e8a2f1b-5c7d-4f9e-8a3b-6d1e2f3a4b5c/cover_letter.pdf",
                  "relative_time": "a few seconds ago",
                  "file": {
                    "is_image": false,
                    "orig_file_name": "cover_letter.pdf",
                    "file_ext": "pdf",
                    "file_type": "application/pdf",
                    "readable_size": "100 KB"
                  }
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Uploads a new file for a candidate using base64 payload. Useful for resume ingestion, portfolio uploads, and post-processing pipelines."
      }
    },
    "/candidates/{id}/resume": {
      "get": {
        "tags": [
          "Candidates"
        ],
        "summary": "Get candidate resume",
        "operationId": "getCandidateResume",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          },
          {
            "name": "include",
            "in": "query",
            "description": "Comma-separated list of optional fields to include. Supported: `text_content` — parsed plain-text content of the resume file.",
            "schema": {
              "type": "string",
              "example": "text_content"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Resume file",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CandidateResumeResponse"
                },
                "example": {
                  "uuid": "7a3c0d5f-8b4e-4a9f-9e1c-2a3b4c5d6e7f",
                  "url": "https://api.100hires.com/v2/attachments/candidate/7a3c0d5f-8b4e-4a9f-9e1c-2a3b4c5d6e7f/john_doe_resume.pdf",
                  "relative_time": "2 days ago",
                  "file": {
                    "is_image": false,
                    "orig_file_name": "john_doe_resume.pdf",
                    "file_ext": "pdf",
                    "file_type": "application/pdf",
                    "readable_size": "240 KB"
                  },
                  "text": "John Doe\nSenior Developer\n\nExperience:\n- Acme Corp, 2019-2024\n- Beta Inc, 2016-2019"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns the primary candidate resume with file metadata. Use `?include=text_content` to get the parsed plain-text content without downloading and parsing the file yourself."
      }
    },
    "/candidates/{id}/activities": {
      "get": {
        "tags": [
          "Candidates"
        ],
        "summary": "List candidate activities",
        "operationId": "listCandidateActivities",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          },
          {
            "name": "page",
            "in": "query",
            "description": "Page number (1-based).",
            "schema": {
              "type": "integer",
              "minimum": 1
            }
          },
          {
            "name": "size",
            "in": "query",
            "description": "Page size. Values above 100 are rejected with 400. Default 20, max 100.",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 20
            }
          },
          {
            "name": "event_type",
            "in": "query",
            "description": "Comma-separated list of event types to filter by. Supported: `comment`, `copilot_response`, `stage_moved`, `automation_action_triggered`, `assign_job`, `enrichment`, `call`, `validate_emails`, `profile_mutation`, `qualification`, `assign_tags`, `assign_sources`, `candidate_rate`.",
            "schema": {
              "type": "string",
              "example": "comment,copilot_response"
            }
          },
          {
            "name": "since",
            "in": "query",
            "description": "Inclusive lower bound on event timestamp. Accepts a Unix timestamp (seconds) or an ISO-8601 string with timezone offset (e.g. `2026-04-01T00:00:00Z`, `2026-04-01T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1737504000,
                "summary": "Unix timestamp"
              },
              "iso8601": {
                "value": "2026-01-22T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "until",
            "in": "query",
            "description": "Inclusive upper bound on event timestamp. Accepts a Unix timestamp (seconds) or an ISO-8601 string with timezone offset (e.g. `2026-04-01T00:00:00Z`, `2026-04-01T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1740268799,
                "summary": "Unix timestamp"
              },
              "iso8601": {
                "value": "2026-02-22T23:59:59Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Candidate activities",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ActivityListResponse"
                },
                "example": {
                  "activities": [
                    {
                      "event_id": 80001,
                      "candidate_id": 12345,
                      "application_id": 501,
                      "user_id": 42,
                      "event": {
                        "type": "stage_moved",
                        "is_text_bubble": true,
                        "data": {
                          "text": "Moved from <b>Applied</b> to <b>Interview</b>",
                          "date": "Mar 22",
                          "relative_time": "2 days ago",
                          "full_time": "2024-03-22 10:30:00"
                        }
                      },
                      "created_at": 1711100200
                    },
                    {
                      "event_id": 80002,
                      "candidate_id": 12345,
                      "application_id": null,
                      "user_id": 42,
                      "event": {
                        "type": "comment",
                        "comment": {
                          "id": 3001,
                          "candidate_id": 12345,
                          "user_id": 42,
                          "author": "Jane Smith",
                          "photo": "https://app.100hires.com/photos/42.jpg",
                          "text": "Strong technical skills, recommend for next round.",
                          "date": "Mar 22",
                          "datetime": "2024-03-22 14:00:00",
                          "relative_time": "2 days ago",
                          "visible": "all",
                          "is_edit": false,
                          "attachments": [

                          ]
                        }
                      },
                      "created_at": 1711112400
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 2
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns timeline activities for a candidate with pagination. Use `?event_type=comment,copilot_response` to filter by specific event types, and `?since=…&until=…` (Unix timestamp in seconds) to constrain the time window."
      }
    },
    "/candidates/{id}/disqualify": {
      "post": {
        "tags": [
          "Candidates"
        ],
        "summary": "Disqualify candidate from active applications",
        "operationId": "disqualifyCandidate",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CandidateDisqualifyRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Disqualified",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CandidateDisqualifyResponse"
                },
                "example": {
                  "success": true,
                  "rejected_applications": [
                    501,
                    502
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Disqualifies candidate applications in one action and returns affected application IDs. Typical for policy-driven rejection or bulk automation rules."
      }
    },
    "/candidates/{id}/interviews": {
      "get": {
        "tags": [
          "Interviews"
        ],
        "summary": "List candidate interviews",
        "operationId": "listCandidateInterviews",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Interview list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/InterviewListResponse"
                },
                "example": {
                  "interviews": [
                    {
                      "id": 7001,
                      "application_id": 501,
                      "job_id": 123,
                      "candidate_id": 12345,
                      "start_time": 1711195200,
                      "end_time": 1711198800,
                      "status": "scheduled",
                      "interviewers": [
                        {
                          "user_id": 42,
                          "name": "Jane Smith",
                          "email": "jane.smith@example.com"
                        }
                      ],
                      "location": null,
                      "meeting_url": "https://meet.google.com/abc-defg-hij",
                      "stage": {
                        "id": 10,
                        "name": "Interview"
                      },
                      "created_at": 1711036800,
                      "updated_at": 1711036800,
                      "last_message_at": null,
                      "days_since_last_message": null
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns all interviews linked to a candidate across all their applications. Useful for candidate timeline views and scheduling conflict detection."
      }
    },
    "/candidates/{id}/messages": {
      "get": {
        "tags": [
          "Messages"
        ],
        "summary": "List candidate messages",
        "operationId": "listCandidateMessages",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          },
          {
            "name": "is_scheduled",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "enum": [
                1
              ]
            },
            "description": "When set to `1`, returns only scheduled (not yet sent) messages. Useful for auditing pending outreach."
          }
        ],
        "responses": {
          "200": {
            "description": "Message list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CandidateMessageListResponse"
                },
                "example": {
                  "messages": [
                    {
                      "type": "mailbox",
                      "is_sent_by_candidate": false,
                      "message": {
                        "id": 60001,
                        "from": "recruiter@example.com",
                        "to": "john.doe@example.com",
                        "cc": "",
                        "subject": "Exciting opportunity at Acme Corp",
                        "body": "<p>Hi John, I came across your profile and wanted to reach out...</p>",
                        "date": "2024-03-22 09:00:00",
                        "attachments": [

                        ],
                        "schedule": "",
                        "opensCount": 2,
                        "opens": [

                        ],
                        "autoJobId": 123,
                        "isNurtured": false
                      }
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated email and messaging history for a candidate. Useful for communication timeline and audit trails. Use `is_scheduled=1` to filter only scheduled (pending) messages."
      },
      "post": {
        "tags": [
          "Messages"
        ],
        "summary": "Create scheduled message for candidate",
        "operationId": "createCandidateMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ScheduledEmailCreateRequest"
              },
              "example": {
                "to": [
                  "alice@example.com"
                ],
                "subject": "Interview invitation — Senior Engineer",
                "body": "<p>Hi Alice, we'd like to invite you for an interview.</p>",
                "from_account_id": 1,
                "application_id": 789
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created scheduled message",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ScheduledEmail"
                },
                "example": {
                  "type": "mailbox",
                  "message": {
                    "id": 60010,
                    "from": "recruiter@example.com",
                    "to": "alice@example.com",
                    "cc": "",
                    "subject": "Interview invitation — Senior Engineer",
                    "body": "<p>Hi Alice, we'd like to invite you for an interview.</p>",
                    "date": "Mar 22, 2024 09:00 AM",
                    "attachments": [

                    ],
                    "schedule": {
                      "senderId": 1,
                      "isForceSend": false,
                      "isFailed": false,
                      "scheduleSendError": null,
                      "isScheduled": true,
                      "scheduledDay": "Mar 22, 2024",
                      "sendAt": 1711098000,
                      "humanDatetime": "Mar 22, 2024 09:00 AM",
                      "systemDatetime": "2024-03-22 09:00:00"
                    },
                    "opensCount": 0,
                    "opens": [

                    ],
                    "autoJobId": "",
                    "isNurtured": false
                  }
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Creates a candidate message through mailbox scheduler. If `scheduled_at` is omitted, the message is scheduled for 15 minutes after creation instead of being sent immediately."
      }
    },
    "/messages": {
      "get": {
        "tags": [
          "Messages"
        ],
        "summary": "List messages by mail account",
        "operationId": "listAccountMessages",
        "parameters": [
          {
            "name": "from_account_id",
            "in": "query",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "ID of the mail account (from `GET /companies/mail-accounts` or `GET /users/{user_id}/mail-accounts`)."
          },
          {
            "name": "status",
            "in": "query",
            "schema": {
              "type": "string",
              "enum": [
                "scheduled",
                "sent",
                "all"
              ],
              "default": "all"
            },
            "description": "Filter by message status: `scheduled` (pending send), `sent` (delivered), `all` (both). Default: `all`."
          },
          {
            "name": "date_from",
            "in": "query",
            "schema": {
              "type": "integer"
            },
            "description": "Start of period (unix timestamp, seconds). Filters on scheduled/sent time."
          },
          {
            "name": "date_to",
            "in": "query",
            "schema": {
              "type": "integer"
            },
            "description": "End of period (unix timestamp, seconds). Filters on scheduled/sent time."
          },
          {
            "name": "page",
            "in": "query",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "default": 1
            },
            "description": "Page number (1-based)."
          },
          {
            "name": "size",
            "in": "query",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 20
            },
            "description": "Number of items per page (1–100)."
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Paginated list of messages for the specified mail account.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AccountMessageListResponse"
                },
                "example": {
                  "messages": [
                    {
                      "type": "mailbox",
                      "message": {
                        "id": 12345,
                        "from": "sender@example.com",
                        "to": "prospect@company.com",
                        "cc": "",
                        "subject": "Exciting opportunity",
                        "body": "<p>Hi, I found your profile...</p>",
                        "date": "Apr 09, 2026 10:00 AM",
                        "attachments": [

                        ],
                        "schedule": "",
                        "opensCount": 2,
                        "opens": [

                        ],
                        "autoJobId": "",
                        "isNurtured": false
                      }
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 7,
                    "page": 1,
                    "total_count": 134
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns messages sent or scheduled from a specific mail account. Useful for monitoring cold outreach campaigns — check pending queue, delivery history, and plan next sends. Only returns outbound messages (sent and scheduled), not received."
      }
    },
    "/messages/{id}": {
      "get": {
        "tags": [
          "Messages"
        ],
        "summary": "Get scheduled message",
        "operationId": "getMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Scheduled message",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ScheduledEmail"
                },
                "example": {
                  "type": "mailbox",
                  "message": {
                    "id": 60010,
                    "from": "recruiter@example.com",
                    "to": "alice@example.com",
                    "cc": "",
                    "subject": "Interview invitation — Senior Engineer",
                    "body": "<p>Hi Alice, we'd like to invite you for an interview.</p>",
                    "date": "Mar 22, 2024 09:00 AM",
                    "attachments": [

                    ],
                    "schedule": {
                      "senderId": 1,
                      "isForceSend": false,
                      "isFailed": false,
                      "scheduleSendError": null,
                      "isScheduled": true,
                      "scheduledDay": "Mar 22, 2024",
                      "sendAt": 1711098000,
                      "humanDatetime": "Mar 22, 2024 09:00 AM",
                      "systemDatetime": "2024-03-22 09:00:00"
                    },
                    "opensCount": 0,
                    "opens": [

                    ],
                    "autoJobId": "",
                    "isNurtured": false
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns scheduler-backed message details, including sender account, schedule timestamps, and cancelability."
      },
      "put": {
        "tags": [
          "Messages"
        ],
        "summary": "Update scheduled message",
        "operationId": "updateMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ScheduledEmailUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated scheduled message",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ScheduledEmail"
                },
                "example": {
                  "type": "mailbox",
                  "message": {
                    "id": 60010,
                    "from": "recruiter@example.com",
                    "to": "alice@example.com",
                    "cc": "",
                    "subject": "Interview invitation — Senior Engineer (updated)",
                    "body": "<p>Hi Alice, we've moved your interview to Friday.</p>",
                    "date": "Mar 22, 2024 09:00 AM",
                    "attachments": [

                    ],
                    "schedule": {
                      "senderId": 1,
                      "isForceSend": false,
                      "isFailed": false,
                      "scheduleSendError": null,
                      "isScheduled": true,
                      "scheduledDay": "Mar 24, 2024",
                      "sendAt": 1711270800,
                      "humanDatetime": "Mar 24, 2024 09:00 AM",
                      "systemDatetime": "2024-03-24 09:00:00"
                    },
                    "opensCount": 0,
                    "opens": [

                    ],
                    "autoJobId": "",
                    "isNurtured": false
                  }
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Rewrites a scheduled message before send time. The same endpoint also accepts PATCH for partial updates."
      },
      "patch": {
        "tags": [
          "Messages"
        ],
        "summary": "Partially update scheduled message",
        "operationId": "patchMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ScheduledEmailUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated scheduled message",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ScheduledEmail"
                },
                "example": {
                  "type": "mailbox",
                  "message": {
                    "id": 60010,
                    "from": "recruiter@example.com",
                    "to": "alice@example.com",
                    "cc": "",
                    "subject": "Interview invitation — Senior Engineer (updated)",
                    "body": "<p>Hi Alice, we've moved your interview to Friday.</p>",
                    "date": "Mar 22, 2024 09:00 AM",
                    "attachments": [

                    ],
                    "schedule": {
                      "senderId": 1,
                      "isForceSend": false,
                      "isFailed": false,
                      "scheduleSendError": null,
                      "isScheduled": true,
                      "scheduledDay": "Mar 24, 2024",
                      "sendAt": 1711270800,
                      "humanDatetime": "Mar 24, 2024 09:00 AM",
                      "systemDatetime": "2024-03-24 09:00:00"
                    },
                    "opensCount": 0,
                    "opens": [

                    ],
                    "autoJobId": "",
                    "isNurtured": false
                  }
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Partially updates a scheduled message before send time."
      },
      "delete": {
        "tags": [
          "Messages"
        ],
        "summary": "Cancel scheduled message",
        "operationId": "cancelMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Message canceled",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Cancels a scheduled message before it is processed by mailbox scheduler."
      }
    },
    "/messages/batch/create": {
      "post": {
        "tags": [
          "Messages"
        ],
        "summary": "Batch create scheduled messages",
        "operationId": "batchCreateMessages",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchCreateMessagesRequest"
              },
              "example": {
                "messages": [
                  {
                    "candidate_id": 1,
                    "to": [
                      "alice@example.com"
                    ],
                    "subject": "Interview invitation",
                    "body": "<p>Hi Alice, we'd like to invite you.</p>",
                    "from_account_id": 1,
                    "scheduled_at": 1700003600
                  },
                  {
                    "candidate_id": 2,
                    "to": [
                      "bob@example.com"
                    ],
                    "subject": "Follow-up",
                    "body": "<p>Hi Bob, following up on our chat.</p>",
                    "from_account_id": 1
                  }
                ]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Batch results with per-item success or error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchCreateMessagesResponse"
                },
                "example": {
                  "results": [
                    {
                      "index": 0,
                      "candidate_id": 1,
                      "data": {
                        "type": "mailbox",
                        "message": {
                          "id": 501,
                          "from": "user@company.com",
                          "to": "alice@example.com",
                          "subject": "Interview invitation"
                        }
                      }
                    },
                    {
                      "index": 1,
                      "candidate_id": 2,
                      "error": {
                        "name": "Not Found",
                        "message": "Candidate not found",
                        "status": 404
                      }
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Creates up to 100 scheduled messages in one request. Each item specifies its own `candidate_id` and message payload. Items are processed independently — one failure does not stop others. Per-candidate RBAC is enforced for each item."
      }
    },
    "/candidates/batch/tags": {
      "post": {
        "tags": [
          "Candidates"
        ],
        "summary": "Batch add tags to candidates",
        "operationId": "batchTagsCandidates",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchTagsCandidatesRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Batch results with per-item success/failure",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchResultResponse"
                },
                "example": {
                  "results": [
                    {
                      "id": 12345,
                      "data": {
                        "tags": [
                          "Senior",
                          "Engineering",
                          "Remote"
                        ]
                      }
                    },
                    {
                      "id": "dtGeby2",
                      "error": {
                        "name": "Not Found",
                        "message": "Candidate not found",
                        "status": 404
                      }
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Adds tags to multiple candidates in one request. Accepts candidate IDs or aliases. Returns per-item results with partial success support."
      },
      "delete": {
        "tags": [
          "Candidates"
        ],
        "summary": "Batch remove tags from candidates",
        "operationId": "batchDeleteTagsCandidates",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchTagsCandidatesRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Batch results with per-item success/failure",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchResultResponse"
                },
                "example": {
                  "results": [
                    {
                      "id": 12345,
                      "data": {
                        "tags": [

                        ]
                      }
                    },
                    {
                      "id": "dtGeby2",
                      "error": {
                        "name": "Not Found",
                        "message": "Candidate not found",
                        "status": 404
                      }
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Removes specified tags from multiple candidates in one request. Returns per-item results with partial success support."
      }
    },
    "/notification-messages/{id}": {
      "get": {
        "tags": [
          "Notification Messages"
        ],
        "summary": "Get notification message",
        "operationId": "getNotificationMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Notification message",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/NotificationMessage"
                },
                "example": {
                  "id": 70001,
                  "from": "notifications@example.com",
                  "to": "john.doe@example.com",
                  "subject": "Update on your application",
                  "body": "<p>Thank you for applying. Unfortunately we have decided to move forward with other candidates.</p>",
                  "date": "Mar 22, 2024 09:00 AM",
                  "schedule": {
                    "id": 8801,
                    "isScheduled": true,
                    "isFailed": false,
                    "humanDatetime": "Mar 22, 2024 09:00 AM",
                    "isNotificationMessage": true
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns a notification email message (e.g. rejection email) by its ID, including subject, body, sender, recipient, and schedule metadata."
      },
      "put": {
        "tags": [
          "Notification Messages"
        ],
        "summary": "Update notification message",
        "operationId": "updateNotificationMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/NotificationMessageUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated notification message",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/NotificationMessage"
                },
                "example": {
                  "id": 70001,
                  "from": "notifications@example.com",
                  "to": "john.doe@example.com",
                  "subject": "Update on your application (revised)",
                  "body": "<p>Thank you for your interest. We'd like to keep your profile on file for future roles.</p>",
                  "date": "Mar 22, 2024 09:00 AM",
                  "schedule": {
                    "id": 8801,
                    "isScheduled": true,
                    "isFailed": false,
                    "humanDatetime": "Mar 24, 2024 09:00 AM",
                    "isNotificationMessage": true
                  }
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Updates subject, body, and optionally reschedules a notification email before it is sent. Only scheduled (not yet sent) messages can be updated."
      },
      "delete": {
        "tags": [
          "Notification Messages"
        ],
        "summary": "Cancel notification message",
        "operationId": "cancelNotificationMessage",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Message canceled",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Cancels a scheduled notification email before it is sent. Already sent messages cannot be canceled."
      }
    },
    "/candidates/{id}/notification-messages": {
      "delete": {
        "tags": [
          "Notification Messages"
        ],
        "summary": "Cancel all notification messages for candidate",
        "operationId": "cancelAllNotificationMessages",
        "parameters": [
          {
            "$ref": "#/components/parameters/CandidateIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "All scheduled notifications canceled",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Cancels all scheduled notification emails for a candidate. Already sent notifications are not affected. Returns success even if no scheduled notifications exist."
      }
    },
    "/applications": {
      "get": {
        "tags": [
          "Applications"
        ],
        "summary": "List applications",
        "operationId": "listApplications",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "name": "candidate_id",
            "in": "query",
            "description": "Filter applications by candidate ID.",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "job_id",
            "in": "query",
            "description": "Filter applications by job ID.",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "stage_id",
            "in": "query",
            "description": "Filter applications by pipeline stage ID. Best used together with job_id.",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "status",
            "in": "query",
            "description": "Filter by application status: `pending` (active), `hired`, or `rejected`.",
            "schema": {
              "type": "string",
              "enum": [
                "pending",
                "hired",
                "rejected"
              ]
            }
          },
          {
            "name": "created_after",
            "in": "query",
            "description": "Return only applications created at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "updated_after",
            "in": "query",
            "description": "Return only applications updated at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds. Use for incremental sync.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "ai_score_min",
            "in": "query",
            "schema": {
              "type": "integer"
            },
            "description": "Return only applications with `ai_score` greater than or equal to this value."
          },
          {
            "name": "ai_score_max",
            "in": "query",
            "schema": {
              "type": "integer"
            },
            "description": "Return only applications with `ai_score` less than or equal to this value."
          },
          {
            "name": "sort",
            "in": "query",
            "schema": {
              "type": "string",
              "enum": [
                "created_at",
                "-created_at",
                "ai_score",
                "-ai_score",
                "last_message_at",
                "-last_message_at"
              ]
            },
            "description": "Sort order. Prefix with `-` for descending. Default: `-created_at`."
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Application list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ApplicationListResponse"
                },
                "examples": {
                  "withCandidate": {
                    "summary": "List applications with nested candidate",
                    "value": {
                      "applications": [
                        {
                          "id": 10,
                          "candidate_id": 10,
                          "job_id": 1,
                          "internal_job_id": "",
                          "company_id": 1,
                          "stage": {
                            "id": 3,
                            "name": "Phone screen"
                          },
                          "status": "active",
                          "is_disqualified": false,
                          "cv": null,
                          "rejected_at": null,
                          "rejection_reason": null,
                          "hired_at": null,
                          "hiring_team": null,
                          "custom_fields": null,
                          "ai_score": null,
                          "ai_recommendation": null,
                          "ai_scoring_updated_at": null,
                          "created_at": 1606348802,
                          "updated_at": 1606348802,
                          "last_message_at": null,
                          "days_since_last_message": null,
                          "candidate": {
                            "id": 10,
                            "company_id": 1,
                            "first_name": "",
                            "last_name": "",
                            "emails": null,
                            "phones": null,
                            "source": null,
                            "origin": {
                              "id": 5,
                              "name": "added_manually"
                            },
                            "profile": [

                            ],
                            "created_at": 1606176005,
                            "updated_at": 1606176005,
                            "last_message_at": null,
                            "days_since_last_message": null,
                            "ip": null
                          }
                        }
                      ],
                      "pagination": {
                        "page": 1,
                        "page_count": 1,
                        "page_size": 25,
                        "total_count": 10
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated applications across accessible companies or for a target company. Supports filtering by AI score range via `ai_score_min` and `ai_score_max`. Core endpoint for pipeline analytics, sync jobs, and ATS dashboards."
      },
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Create application",
        "operationId": "createApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ApplicationCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 10,
                    "name": "New"
                  },
                  "status": "active",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": null,
                  "hiring_team": null,
                  "custom_fields": null,
                  "ai_score": null,
                  "ai_recommendation": null,
                  "ai_scoring_updated_at": null,
                  "created_at": 1711036800,
                  "updated_at": 1711036800,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Creates an application by linking an existing candidate to a job, with optional stage/CV. Use for sourcing workflows and manual application ingestion."
      }
    },
    "/applications/{id}": {
      "get": {
        "tags": [
          "Applications"
        ],
        "summary": "Get application",
        "operationId": "getApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 12,
                    "name": "Phone screen"
                  },
                  "status": "active",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": null,
                  "hiring_team": [
                    {
                      "id": 5,
                      "full_name": "Jane Smith",
                      "email": "jane@example.com",
                      "role": "recruiter"
                    }
                  ],
                  "custom_fields": null,
                  "ai_score": 72,
                  "ai_recommendation": "Probably Yes",
                  "ai_scoring_updated_at": 1711036800,
                  "created_at": 1711036800,
                  "updated_at": 1711123200,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns full application payload with stage/status/rejection context. Recommended before mutating stage transitions in external automations."
      },
      "put": {
        "tags": [
          "Applications"
        ],
        "summary": "Update application",
        "operationId": "updateApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ApplicationUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 14,
                    "name": "Offer"
                  },
                  "status": "active",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": null,
                  "hiring_team": null,
                  "custom_fields": null,
                  "ai_score": 72,
                  "ai_recommendation": "Probably Yes",
                  "ai_scoring_updated_at": 1711036800,
                  "created_at": 1711036800,
                  "updated_at": 1711209600,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Updates application-level fields such as stage, disqualification flag, and CV. Supports external pipeline management and data correction flows."
      },
      "delete": {
        "tags": [
          "Applications"
        ],
        "summary": "Delete application",
        "operationId": "deleteApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Application deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes an application and removes it from default list/view queries."
      }
    },
    "/applications/{id}/ai-score": {
      "get": {
        "tags": [
          "Applications"
        ],
        "summary": "Get application AI score",
        "operationId": "getApplicationAiScore",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Structured AI score payload for the latest application scoring result",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ApplicationAiScoreResponse"
                },
                "example": {
                  "score": {
                    "uuid": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
                    "job_id": 7,
                    "job_title": "Senior Backend Developer",
                    "job_url": "https://app.100hires.com/jobs/7",
                    "summary": "Strong backend experience with relevant tech stack. Could improve on system design depth.",
                    "total_score": 72,
                    "criteria": [
                      {
                        "criterion_title": "Technical Skills",
                        "criterion_text": "Proficiency in required programming languages and frameworks",
                        "score": 80,
                        "justification": "Demonstrated strong PHP and Python skills with 5+ years of experience.",
                        "followup_questions": [
                          "Can you describe your experience with distributed systems?"
                        ]
                      },
                      {
                        "criterion_title": "Experience",
                        "criterion_text": "Relevant industry and role experience",
                        "score": 65,
                        "justification": "Has backend experience but limited exposure to high-scale systems.",
                        "followup_questions": null
                      }
                    ],
                    "rate": 72,
                    "date": "2024-03-22"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns the latest machine-readable AI score for an application. This is separate from candidate timeline `copilot_response` events and returns the same structured payload shape as `ManageEvaluation::toArrayApplicationScore`."
      }
    },
    "/applications/{id}/stage-history": {
      "get": {
        "tags": [
          "Applications"
        ],
        "summary": "Get application stage history",
        "operationId": "listApplicationStageHistory",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Full chronological stage transition history for an application, including the initial assignment.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ApplicationStageHistoryResponse"
                },
                "example": {
                  "history": [
                    {
                      "from_stage_id": null,
                      "from_stage_name": null,
                      "to_stage_id": 15941,
                      "to_stage_name": "Applied",
                      "moved_at": 1731713700,
                      "moved_by_type": "system",
                      "moved_by_user_id": null
                    },
                    {
                      "from_stage_id": 15941,
                      "from_stage_name": "Applied",
                      "to_stage_id": 16827,
                      "to_stage_name": "Send screening email",
                      "moved_at": 1731713760,
                      "moved_by_type": "automation",
                      "moved_by_user_id": null
                    },
                    {
                      "from_stage_id": 16827,
                      "from_stage_name": "Send screening email",
                      "to_stage_id": 16828,
                      "to_stage_name": "Technical interview",
                      "moved_at": 1731800100,
                      "moved_by_type": "user",
                      "moved_by_user_id": 42
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns the ordered list of stage transitions for one application — including the initial stage assignment (where `from_stage_id` is `null`) — in a single response.\n\nUse this instead of paginating through `/candidates/{id}/activities` when you only need stage-transition data (funnel analysis, time-in-stage reports).\n\n`moved_by_type` is one of:\n  - `user` — manual move by an authenticated user (`moved_by_user_id` is set)\n  - `automation` — move driven by an automation rule / form watcher\n  - `system` — initial assignment or other non-user, non-automation source"
      }
    },
    "/applications/{id}/move": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Move application to stage",
        "operationId": "moveApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ApplicationMoveRequest"
              },
              "example": {
                "stage_id": 456
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 456,
                    "name": "Technical interview"
                  },
                  "status": "active",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": null,
                  "hiring_team": null,
                  "custom_fields": null,
                  "ai_score": 72,
                  "ai_recommendation": "Probably Yes",
                  "ai_scoring_updated_at": 1711036800,
                  "created_at": 1711036800,
                  "updated_at": 1711209600,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Moves an application to a specific pipeline stage. This is the explicit stage transition endpoint for workflow orchestration."
      }
    },
    "/applications/{id}/hire": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Mark application as hired",
        "operationId": "hireApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Updated application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 15,
                    "name": "Hired"
                  },
                  "status": "hired",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": 1711296000,
                  "hiring_team": [
                    {
                      "id": 5,
                      "full_name": "Jane Smith",
                      "email": "jane@example.com",
                      "role": "recruiter"
                    }
                  ],
                  "custom_fields": null,
                  "ai_score": 85,
                  "ai_recommendation": "Strong Yes",
                  "ai_scoring_updated_at": 1711036800,
                  "created_at": 1711036800,
                  "updated_at": 1711296000,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Marks an application as hired using domain rules from the current workflow. Use as the finalization step in hiring automations."
      }
    },
    "/applications/{id}/reject": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Reject application",
        "operationId": "rejectApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ApplicationRejectRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 12,
                    "name": "Phone screen"
                  },
                  "status": "rejected",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": 1711209600,
                  "rejection_reason": [
                    {
                      "id": 3,
                      "name": "Not enough experience"
                    }
                  ],
                  "hired_at": null,
                  "hiring_team": null,
                  "custom_fields": null,
                  "ai_score": 72,
                  "ai_recommendation": "Probably Yes",
                  "ai_scoring_updated_at": 1711036800,
                  "created_at": 1711036800,
                  "updated_at": 1711209600,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Rejects an application with optional rejection reason and note context. Standard endpoint for rejection workflows and reporting consistency."
      }
    },
    "/applications/{id}/advance": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Advance application to next stage",
        "operationId": "advanceApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Updated application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 13,
                    "name": "Technical interview"
                  },
                  "status": "active",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": null,
                  "hiring_team": null,
                  "custom_fields": null,
                  "ai_score": 72,
                  "ai_recommendation": "Probably Yes",
                  "ai_scoring_updated_at": 1711036800,
                  "created_at": 1711036800,
                  "updated_at": 1711209600,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Advances the application to the next stage according to workflow order."
      }
    },
    "/applications/{id}/transfer": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Transfer application to another job",
        "operationId": "transferApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ApplicationTransferRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 510,
                  "candidate_id": 42,
                  "job_id": 15,
                  "job_alias": "Kx9mPqW",
                  "internal_job_id": "ENG-042",
                  "company_id": 1,
                  "stage": {
                    "id": 20,
                    "name": "New"
                  },
                  "status": "active",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": null,
                  "hiring_team": null,
                  "custom_fields": null,
                  "ai_score": null,
                  "ai_recommendation": null,
                  "ai_scoring_updated_at": null,
                  "created_at": 1711209600,
                  "updated_at": 1711209600,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Transfers an application to another job with optional target stage."
      }
    },
    "/applications/{id}/unreject": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Undo application rejection",
        "operationId": "unrejectApplication",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ApplicationIncludeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Updated application",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Application"
                },
                "example": {
                  "id": 501,
                  "candidate_id": 42,
                  "job_id": 7,
                  "job_alias": "79SZHfT",
                  "internal_job_id": "",
                  "company_id": 1,
                  "stage": {
                    "id": 12,
                    "name": "Phone screen"
                  },
                  "status": "active",
                  "is_disqualified": false,
                  "cv": null,
                  "rejected_at": null,
                  "rejection_reason": null,
                  "hired_at": null,
                  "hiring_team": null,
                  "custom_fields": null,
                  "ai_score": 72,
                  "ai_recommendation": "Probably Yes",
                  "ai_scoring_updated_at": 1711036800,
                  "created_at": 1711036800,
                  "updated_at": 1711209600,
                  "last_message_at": null,
                  "days_since_last_message": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Reopens a previously rejected application. Use for recovery flows, reconsideration pipelines, and human override operations."
      }
    },
    "/applications/{id}/evaluation-forms": {
      "get": {
        "tags": [
          "Evaluations"
        ],
        "summary": "List filled evaluation forms for application",
        "operationId": "listApplicationEvaluationForms",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "List of filled evaluations",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EvaluationListResponse"
                },
                "example": {
                  "evaluations": [
                    {
                      "id": 301,
                      "application_id": 501,
                      "form_id": 5,
                      "form_name": "Technical Interview",
                      "user": {
                        "id": 12,
                        "full_name": "Alice Johnson"
                      },
                      "summary_score": "strong-yes",
                      "summary_text": "Excellent problem-solving skills and strong system design knowledge.",
                      "created_at": 1711209600,
                      "updated_at": 1711209600
                    },
                    {
                      "id": 302,
                      "application_id": 501,
                      "form_id": 6,
                      "form_name": "Culture Fit",
                      "user": {
                        "id": 15,
                        "full_name": "Bob Williams"
                      },
                      "summary_score": "probably-yes",
                      "summary_text": "Good team player, aligns well with company values.",
                      "created_at": 1711296000,
                      "updated_at": 1711296000
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns all filled evaluation forms for an application. Each evaluation includes the evaluator, score, and summary text."
      }
    },
    "/evaluation-forms/{id}": {
      "get": {
        "tags": [
          "Evaluations"
        ],
        "summary": "Get filled evaluation form with answers",
        "operationId": "getEvaluationForm",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Evaluation with answers",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EvaluationDetail"
                },
                "example": {
                  "id": 301,
                  "application_id": 501,
                  "form_id": 5,
                  "form_name": "Technical Interview",
                  "user": {
                    "id": 12,
                    "full_name": "Alice Johnson"
                  },
                  "summary_score": "strong-yes",
                  "summary_text": "Excellent problem-solving skills and strong system design knowledge.",
                  "created_at": 1711209600,
                  "updated_at": 1711209600,
                  "answers": [
                    {
                      "question_id": 1,
                      "question_text": "How would you rate the candidate's coding skills?",
                      "value": "5"
                    },
                    {
                      "question_id": 2,
                      "question_text": "How well does the candidate communicate technical concepts?",
                      "value": "4"
                    },
                    {
                      "question_id": 3,
                      "question_text": "Additional comments",
                      "value": "Strong candidate with deep backend expertise."
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns a single filled evaluation form with all answers. Use for detailed review of evaluator feedback."
      }
    },
    "/attachments/{category}/{uuid}/{file_name}": {
      "get": {
        "tags": [
          "Attachments"
        ],
        "summary": "Download attachment bytes",
        "operationId": "downloadAttachment",
        "description": "Streams the raw file bytes for an attachment identified by `category` + `uuid`.\n\nThe full URL is pre-built and returned in other API responses (resume, candidate files, application attachments, message attachments, call recordings). Clients should follow the URL as-is with the same `Authorization: Bearer` header used elsewhere.\n\nVisibility rules: the attachment must belong to a company accessible by the authenticated API key (partner + clients, or the authenticated company itself). Shadowed candidates return 404.\n\nThe response sets `Content-Disposition: attachment; filename=\"...\"` with the original filename (not the internal hashed name in the URL).\n",
        "parameters": [
          {
            "name": "category",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "enum": [
                "application",
                "candidate",
                "candidate_comment",
                "call_recording",
                "company_favicon",
                "company_header",
                "company_link_preview",
                "email_template",
                "export_csv",
                "import_cv",
                "job_note",
                "job_preview",
                "mail_attachment",
                "qas",
                "system",
                "voicemail"
              ]
            },
            "description": "Attachment category (matches the segment in the returned URL)."
          },
          {
            "name": "uuid",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "format": "uuid"
            },
            "description": "Attachment UUID."
          },
          {
            "name": "file_name",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Internal storage filename segment from the URL. Required for the route to match; the `Content-Disposition` header on the response carries the human-readable original filename."
          }
        ],
        "responses": {
          "200": {
            "description": "Raw file bytes.",
            "headers": {
              "Content-Type": {
                "schema": {
                  "type": "string"
                },
                "description": "MIME type of the file (e.g. `application/pdf`, `application/vnd.openxmlformats-officedocument.wordprocessingml.document`)."
              },
              "Content-Length": {
                "schema": {
                  "type": "integer"
                },
                "description": "File size in bytes."
              },
              "Content-Disposition": {
                "schema": {
                  "type": "string"
                },
                "description": "Always `attachment; filename=\"...\"` with the original filename."
              }
            },
            "content": {
              "application/octet-stream": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        }
      }
    },
    "/attachments": {
      "post": {
        "tags": [
          "Attachments"
        ],
        "summary": "Upload attachment",
        "operationId": "uploadAttachment",
        "description": "Uploads a file and creates an attachment in the authenticated company.\n\nSupported categories. The attachment is stored under `company_id` (if provided — must be accessible by the API key) or the authenticated company by default. The referenced `object_id` must belong to that same company (strict `company_id` match, no cross-company uploads).\n- `voicemail` — audio file (wav/mp3, ≤20 MB). No `object_id` required. Returned `uuid` can be referenced as `attachment_uuid` in nurture-campaign voicemail steps.\n- `candidate` — generic candidate file. `object_id` = candidate ID.\n- `application` — application attachment (signed docs, offer letters, etc.). `object_id` = application ID.\n- `candidate_comment` — attachment for a candidate comment. `object_id` = comment ID.\n- `job_note` — attachment for a job note. `object_id` = job note ID.\n- `company_favicon`, `company_header`, `company_link_preview` — company branding assets. `object_id` = company ID (must match the authenticated company or a client company the API key can access).\n\nReturns `ApiAttachment`. Follow `url` with the same Bearer token to download the file later.\n",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/UploadApiAttachmentRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Uploaded attachment",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ApiAttachment"
                },
                "example": {
                  "uuid": "9f8e7d6c-5b4a-3210-9f8e-7d6c5b4a3210",
                  "url": "https://api.100hires.com/v2/attachments/voicemail/9f8e7d6c-5b4a-3210-9f8e-7d6c5b4a3210/welcome_message.mp3",
                  "relative_time": "just now",
                  "file": {
                    "is_image": false,
                    "orig_file_name": "welcome_message.mp3",
                    "file_ext": "mp3",
                    "file_type": "audio/mpeg",
                    "readable_size": "512 KB"
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        }
      }
    },
    "/applications/{id}/attachments": {
      "get": {
        "tags": [
          "Applications"
        ],
        "summary": "List application attachments",
        "operationId": "listApplicationAttachments",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Attachment list",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/ApplicationAttachment"
                  }
                },
                "example": [
                  {
                    "uuid": "55aaaaaa-bbbb-cccc-dddd-555555555555",
                    "url": "https://api.100hires.com/v2/attachments/application/55aaaaaa-bbbb-cccc-dddd-555555555555/resume_john_doe.pdf",
                    "relative_time": "2 days ago",
                    "file": {
                      "is_image": false,
                      "orig_file_name": "resume_john_doe.pdf",
                      "file_ext": "pdf",
                      "file_type": "application/pdf",
                      "readable_size": "100 KB"
                    }
                  },
                  {
                    "uuid": "56bbbbbb-cccc-dddd-eeee-666666666666",
                    "url": "https://api.100hires.com/v2/attachments/application/56bbbbbb-cccc-dddd-eeee-666666666666/cover_letter.docx",
                    "relative_time": "1 day ago",
                    "file": {
                      "is_image": false,
                      "orig_file_name": "cover_letter.docx",
                      "file_ext": "docx",
                      "file_type": "application/vnd.openxmlformats-officedocument.wordprocessingml.document",
                      "readable_size": "50 KB"
                    }
                  }
                ]
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Lists attachments linked to an application."
      },
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Upload application attachment",
        "operationId": "uploadApplicationAttachment",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ApplicationAttachmentUploadRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Uploaded attachment",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ApplicationAttachment"
                },
                "example": {
                  "uuid": "88cccccc-dddd-eeee-ffff-888888888888",
                  "url": "https://api.100hires.com/v2/attachments/application/88cccccc-dddd-eeee-ffff-888888888888/offer_letter.pdf",
                  "relative_time": "a few seconds ago",
                  "file": {
                    "is_image": false,
                    "orig_file_name": "offer_letter.pdf",
                    "file_ext": "pdf",
                    "file_type": "application/pdf",
                    "readable_size": "200 KB"
                  },
                  "created_at": 1711036800
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Uploads an attachment directly to the application context. Commonly used for signed documents and interviewer artifacts."
      }
    },
    "/applications/batch/move": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Batch move applications to stage",
        "operationId": "batchMoveApplications",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchMoveApplicationsRequest"
              },
              "example": {
                "ids": [
                  101,
                  102,
                  103
                ],
                "stage_id": 456
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Batch results with per-item success/failure",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchResultResponse"
                },
                "example": {
                  "results": [
                    {
                      "id": 101,
                      "success": true
                    },
                    {
                      "id": 102,
                      "success": true
                    },
                    {
                      "id": 103,
                      "success": false,
                      "error": "Application not found"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Moves multiple applications to a specified pipeline stage in one request. Returns per-item results with partial success support."
      }
    },
    "/applications/batch/reject": {
      "post": {
        "tags": [
          "Applications"
        ],
        "summary": "Batch reject applications",
        "operationId": "batchRejectApplications",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchRejectApplicationsRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Batch results with per-item success/failure",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchResultResponse"
                },
                "example": {
                  "results": [
                    {
                      "id": 201,
                      "success": true
                    },
                    {
                      "id": 202,
                      "success": true
                    },
                    {
                      "id": 203,
                      "success": false,
                      "error": "Application not found"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Rejects multiple applications in one request with optional rejection reason. Returns per-item results with partial success support."
      }
    },
    "/applications/{id}/interviews": {
      "post": {
        "tags": [
          "Interviews"
        ],
        "summary": "Create interview",
        "operationId": "createInterview",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/InterviewIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/InterviewCreateRequest"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Created interview",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Interview"
                },
                "example": {
                  "id": 501,
                  "application_id": 100,
                  "job_id": 10,
                  "candidate_id": 12345,
                  "start_time": 1711180800,
                  "end_time": 1711184400,
                  "status": "scheduled",
                  "interviewers": [
                    {
                      "user_id": 5,
                      "name": "Sarah Connor",
                      "email": "sarah@example.com"
                    }
                  ],
                  "location": "Conference Room A",
                  "meeting_url": "https://zoom.us/j/123456789",
                  "stage": {
                    "id": 3,
                    "name": "Technical interview"
                  },
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Schedules a new interview for an application. Creates a session if none exists for the given date. Location string is resolved to an existing location record or created automatically."
      }
    },
    "/interviews": {
      "get": {
        "tags": [
          "Interviews"
        ],
        "summary": "List interviews",
        "operationId": "listInterviews",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "name": "job_id",
            "in": "query",
            "description": "Filter interviews by job ID.",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "application_id",
            "in": "query",
            "description": "Filter interviews by application ID.",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "candidate_id",
            "in": "query",
            "description": "Filter interviews by candidate ID.",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "interviewer_user_id",
            "in": "query",
            "schema": {
              "type": "integer",
              "example": 1
            },
            "description": "Filter interviews by interviewer user ID. Can be combined with other interview list filters."
          },
          {
            "name": "date",
            "in": "query",
            "description": "Filter by interview date (YYYY-MM-DD, UTC).",
            "schema": {
              "type": "string",
              "format": "date"
            }
          },
          {
            "name": "created_after",
            "in": "query",
            "description": "Return only interviews created at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "updated_after",
            "in": "query",
            "description": "Return only interviews updated at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "$ref": "#/components/parameters/InterviewIncludeQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Interview list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/InterviewListResponse"
                },
                "example": {
                  "interviews": [
                    {
                      "id": 501,
                      "application_id": 100,
                      "job_id": 10,
                      "candidate_id": 12345,
                      "start_time": 1711180800,
                      "end_time": 1711184400,
                      "status": "scheduled",
                      "interviewers": [
                        {
                          "user_id": 5,
                          "name": "Sarah Connor",
                          "email": "sarah@example.com"
                        }
                      ],
                      "location": "Conference Room A",
                      "meeting_url": "https://zoom.us/j/123456789",
                      "stage": {
                        "id": 3,
                        "name": "Technical interview"
                      },
                      "created_at": 1711036800,
                      "updated_at": 1711036800
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns a paginated list of interviews. Supports filtering by job, application, candidate, date, and timestamp for incremental sync."
      }
    },
    "/interviews/{id}": {
      "get": {
        "tags": [
          "Interviews"
        ],
        "summary": "Get interview",
        "operationId": "getInterview",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/InterviewIncludeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Interview",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Interview"
                },
                "example": {
                  "id": 501,
                  "application_id": 100,
                  "job_id": 10,
                  "candidate_id": 12345,
                  "start_time": 1711180800,
                  "end_time": 1711184400,
                  "status": "scheduled",
                  "interviewers": [
                    {
                      "user_id": 5,
                      "name": "Sarah Connor",
                      "email": "sarah@example.com"
                    }
                  ],
                  "location": "Conference Room A",
                  "meeting_url": "https://zoom.us/j/123456789",
                  "stage": {
                    "id": 3,
                    "name": "Technical interview"
                  },
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns full interview details. Use `include` to load related candidate, application, or job payloads."
      }
    },
    "/jobs": {
      "get": {
        "tags": [
          "Jobs"
        ],
        "summary": "List jobs",
        "operationId": "listJobs",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "name": "status",
            "in": "query",
            "description": "Filter by job status name (from GET /taxonomy/statuses, e.g. `Public`, `Draft`, `Archived`).",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "created_at_start",
            "in": "query",
            "description": "Return only jobs created at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "created_at_end",
            "in": "query",
            "description": "Return only jobs created at or before this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "updated_after",
            "in": "query",
            "description": "Return only jobs updated at or after this time. Accepts a Unix timestamp in seconds (not milliseconds) or an ISO-8601 string with timezone offset (e.g. `2026-05-11T00:00:00Z`, `2026-05-11T00:00:00.123+03:00`). Fractional seconds are accepted but truncated to whole seconds. Use for incremental sync.",
            "schema": {
              "oneOf": [
                {
                  "type": "integer",
                  "minimum": 0
                },
                {
                  "type": "string"
                }
              ]
            },
            "examples": {
              "unix": {
                "value": 1778457600,
                "summary": "Unix timestamp (seconds)"
              },
              "iso8601": {
                "value": "2026-05-11T00:00:00Z",
                "summary": "ISO-8601 UTC"
              }
            }
          },
          {
            "name": "department_id",
            "in": "query",
            "description": "Filter jobs by department ID (from GET /taxonomy/departments).",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "q",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Search by job title or internal title (partial match)"
          },
          {
            "$ref": "#/components/parameters/JobIncludeQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Job list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/JobListResponse"
                },
                "example": {
                  "jobs": [
                    {
                      "id": 10,
                      "alias": "79SZHfT",
                      "company_id": 1,
                      "title": "Senior Software Engineer",
                      "internal_title": null,
                      "internal_job_id": null,
                      "description": "<p>We are looking for a senior engineer...</p>",
                      "resume_field_status": "optional",
                      "location": {
                        "city": "San Francisco",
                        "country": "United States",
                        "state": "California",
                        "street_address": null,
                        "full_address": "San Francisco, California, United States",
                        "postal_code": null
                      },
                      "url": "https://100hires.com/career/job/79SZHfT",
                      "is_remote": false,
                      "status": "Public",
                      "department": {
                        "id": 1,
                        "name": "Engineering"
                      },
                      "category": {
                        "id": 2,
                        "name": "Software Development"
                      },
                      "employment_type": {
                        "id": 1,
                        "name": "Full-time"
                      },
                      "education_level": null,
                      "experience_level": {
                        "id": 3,
                        "name": "Senior"
                      },
                      "workflow_id": 1,
                      "workflow": null,
                      "salary_min": 120000,
                      "salary_max": 180000,
                      "salary_currency": "USD",
                      "salary_period": "annually",
                      "hours_per_week_min": null,
                      "hours_per_week_max": null,
                      "indeed_posting_data": {
                      },
                      "hiring_team": [

                      ],
                      "pipeline_stages": null,
                      "is_satellite": false,
                      "parent_job_id": null,
                      "created_at": 1711036800,
                      "updated_at": 1711036800
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated jobs with status/date filters. Use for career-site sync, reporting, and external system indexing."
      },
      "post": {
        "tags": [
          "Jobs"
        ],
        "summary": "Create job",
        "operationId": "createJob",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/JobCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created job",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Job"
                },
                "example": {
                  "id": 10,
                  "alias": "79SZHfT",
                  "company_id": 1,
                  "title": "Senior Software Engineer",
                  "internal_title": null,
                  "internal_job_id": null,
                  "description": "<p>We are looking for a senior engineer...</p>",
                  "resume_field_status": "optional",
                  "location": {
                    "city": "San Francisco",
                    "country": "United States",
                    "state": "California",
                    "street_address": null,
                    "full_address": "San Francisco, California, United States",
                    "postal_code": null
                  },
                  "url": "https://100hires.com/career/job/79SZHfT",
                  "is_remote": false,
                  "status": "Public",
                  "department": {
                    "id": 1,
                    "name": "Engineering"
                  },
                  "category": {
                    "id": 2,
                    "name": "Software Development"
                  },
                  "employment_type": {
                    "id": 1,
                    "name": "Full-time"
                  },
                  "education_level": null,
                  "experience_level": {
                    "id": 3,
                    "name": "Senior"
                  },
                  "workflow_id": 1,
                  "workflow": null,
                  "salary_min": 120000,
                  "salary_max": 180000,
                  "salary_currency": "USD",
                  "salary_period": "annually",
                  "hours_per_week_min": null,
                  "hours_per_week_max": null,
                  "indeed_posting_data": {
                  },
                  "hiring_team": [

                  ],
                  "pipeline_stages": null,
                  "is_satellite": false,
                  "parent_job_id": null,
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Creates a job with taxonomy, location, salary, and workflow configuration. Primary endpoint for programmatic job publishing workflows."
      }
    },
    "/jobs/{id}": {
      "get": {
        "tags": [
          "Jobs"
        ],
        "summary": "Get job",
        "operationId": "getJob",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          },
          {
            "$ref": "#/components/parameters/JobIncludeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Job",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Job"
                },
                "example": {
                  "id": 10,
                  "alias": "79SZHfT",
                  "company_id": 1,
                  "title": "Senior Software Engineer",
                  "internal_title": null,
                  "internal_job_id": null,
                  "description": "<p>We are looking for a senior engineer...</p>",
                  "resume_field_status": "optional",
                  "location": {
                    "city": "San Francisco",
                    "country": "United States",
                    "state": "California",
                    "street_address": null,
                    "full_address": "San Francisco, California, United States",
                    "postal_code": null
                  },
                  "url": "https://100hires.com/career/job/79SZHfT",
                  "is_remote": false,
                  "status": "Public",
                  "department": {
                    "id": 1,
                    "name": "Engineering"
                  },
                  "category": {
                    "id": 2,
                    "name": "Software Development"
                  },
                  "employment_type": {
                    "id": 1,
                    "name": "Full-time"
                  },
                  "education_level": null,
                  "experience_level": {
                    "id": 3,
                    "name": "Senior"
                  },
                  "workflow_id": 1,
                  "workflow": null,
                  "salary_min": 120000,
                  "salary_max": 180000,
                  "salary_currency": "USD",
                  "salary_period": "annually",
                  "hours_per_week_min": null,
                  "hours_per_week_max": null,
                  "indeed_posting_data": {
                  },
                  "hiring_team": [

                  ],
                  "pipeline_stages": null,
                  "is_satellite": false,
                  "parent_job_id": null,
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns the full job payload. Use `include` to load related workflow or hiring team data."
      },
      "put": {
        "tags": [
          "Jobs"
        ],
        "summary": "Update job",
        "operationId": "updateJob",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          },
          {
            "$ref": "#/components/parameters/JobIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/JobUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated job",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Job"
                },
                "example": {
                  "id": 10,
                  "alias": "79SZHfT",
                  "company_id": 1,
                  "title": "Senior Software Engineer",
                  "internal_title": null,
                  "internal_job_id": null,
                  "description": "<p>We are looking for a senior engineer...</p>",
                  "resume_field_status": "optional",
                  "location": {
                    "city": "San Francisco",
                    "country": "United States",
                    "state": "California",
                    "street_address": null,
                    "full_address": "San Francisco, California, United States",
                    "postal_code": null
                  },
                  "url": "https://100hires.com/career/job/79SZHfT",
                  "is_remote": false,
                  "status": "Public",
                  "department": {
                    "id": 1,
                    "name": "Engineering"
                  },
                  "category": {
                    "id": 2,
                    "name": "Software Development"
                  },
                  "employment_type": {
                    "id": 1,
                    "name": "Full-time"
                  },
                  "education_level": null,
                  "experience_level": {
                    "id": 3,
                    "name": "Senior"
                  },
                  "workflow_id": 1,
                  "workflow": null,
                  "salary_min": 120000,
                  "salary_max": 180000,
                  "salary_currency": "USD",
                  "salary_period": "annually",
                  "hours_per_week_min": null,
                  "hours_per_week_max": null,
                  "indeed_posting_data": {
                  },
                  "hiring_team": [

                  ],
                  "pipeline_stages": null,
                  "is_satellite": false,
                  "parent_job_id": null,
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Updates mutable job attributes. Preserves domain-level validation rules."
      },
      "delete": {
        "tags": [
          "Jobs"
        ],
        "summary": "Delete job",
        "operationId": "deleteJob",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes a job. Use to align archived/removed positions across integrated platforms."
      }
    },
    "/jobs/{id}/status": {
      "patch": {
        "tags": [
          "Jobs"
        ],
        "summary": "Update job status",
        "operationId": "updateJobStatus",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          },
          {
            "$ref": "#/components/parameters/JobIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/JobStatusUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated job",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Job"
                },
                "example": {
                  "id": 10,
                  "alias": "79SZHfT",
                  "company_id": 1,
                  "title": "Senior Software Engineer",
                  "internal_title": null,
                  "internal_job_id": null,
                  "description": "<p>We are looking for a senior engineer...</p>",
                  "resume_field_status": "optional",
                  "location": {
                    "city": "San Francisco",
                    "country": "United States",
                    "state": "California",
                    "street_address": null,
                    "full_address": "San Francisco, California, United States",
                    "postal_code": null
                  },
                  "url": "https://100hires.com/career/job/79SZHfT",
                  "is_remote": false,
                  "status": "Draft",
                  "department": {
                    "id": 1,
                    "name": "Engineering"
                  },
                  "category": {
                    "id": 2,
                    "name": "Software Development"
                  },
                  "employment_type": {
                    "id": 1,
                    "name": "Full-time"
                  },
                  "education_level": null,
                  "experience_level": {
                    "id": 3,
                    "name": "Senior"
                  },
                  "workflow_id": 1,
                  "workflow": null,
                  "salary_min": 120000,
                  "salary_max": 180000,
                  "salary_currency": "USD",
                  "salary_period": "annually",
                  "hours_per_week_min": null,
                  "hours_per_week_max": null,
                  "indeed_posting_data": {
                  },
                  "hiring_team": [

                  ],
                  "pipeline_stages": null,
                  "is_satellite": false,
                  "parent_job_id": null,
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Changes job status via dedicated endpoint for status automation. Recommended for publish/unpublish/archive transitions."
      }
    },
    "/jobs/{id}/hiring-team": {
      "get": {
        "tags": [
          "Jobs"
        ],
        "summary": "List job hiring team",
        "operationId": "getJobHiringTeam",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Hiring team",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HiringTeamResponse"
                },
                "example": {
                  "hiring_team": [
                    {
                      "id": 5,
                      "full_name": "Sarah Connor",
                      "email": "sarah@example.com",
                      "role": "hiring_manager"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns users currently assigned to the job hiring team. Useful for notification routing and collaboration tooling."
      },
      "post": {
        "tags": [
          "Jobs"
        ],
        "summary": "Add hiring team member",
        "operationId": "addJobHiringTeamMember",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/HiringTeamAddRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Hiring team",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HiringTeamResponse"
                },
                "example": {
                  "hiring_team": [
                    {
                      "id": 5,
                      "full_name": "Sarah Connor",
                      "email": "sarah@example.com",
                      "role": "hiring_manager"
                    }
                  ]
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Adds a company member to job hiring team assignments. Use in workflow setup and ownership automation."
      }
    },
    "/jobs/{id}/webhooks": {
      "get": {
        "tags": [
          "Jobs"
        ],
        "summary": "List job webhooks",
        "operationId": "listJobWebhooks",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Job webhooks",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookListResponse"
                },
                "example": {
                  "webhooks": [
                    {
                      "id": 1,
                      "url": "https://example.com/webhook"
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Lists webhooks configured for a job-level event stream. Use to audit subscriptions and deployment state."
      },
      "post": {
        "tags": [
          "Jobs"
        ],
        "summary": "Create job webhook",
        "operationId": "createJobWebhook",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/WebhookCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created webhook. `signing_secret` is returned only here — store it securely.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookWithSecret"
                },
                "example": {
                  "id": 1,
                  "url": "https://example.com/webhook",
                  "signing_secret": "3f9a8b7c6d5e4f0a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b0c1d2e3f4a"
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Registers a webhook URL for job-related events. Core step for outbound integration setup."
      }
    },
    "/jobs/{id}/webhooks/{webhook_id}/rotate-secret": {
      "post": {
        "tags": [
          "Jobs"
        ],
        "summary": "Rotate job webhook signing secret",
        "operationId": "rotateJobWebhookSecret",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          },
          {
            "$ref": "#/components/parameters/WebhookIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "New signing secret (the previous one stays valid for a grace window).",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookWithSecret"
                },
                "example": {
                  "id": 1,
                  "url": "https://example.com/webhook",
                  "signing_secret": "9b0c1d2e3f4a5b6c7d8e9f0a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b0c"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Rotates the webhook's signing secret with zero downtime. The previous secret remains valid for a grace window so both old and new `x-hires-signature-v2` signatures are accepted while you switch over."
      }
    },
    "/jobs/{id}/webhooks/{webhook_id}": {
      "delete": {
        "tags": [
          "Jobs"
        ],
        "summary": "Delete job webhook",
        "operationId": "deleteJobWebhook",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          },
          {
            "$ref": "#/components/parameters/WebhookIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Disables a job webhook subscription by ID. Use for cleanup, rotation, and endpoint migration."
      }
    },
    "/jobs/{id}/job-boards": {
      "get": {
        "tags": [
          "Jobs"
        ],
        "summary": "Get job boards state for job",
        "operationId": "getJobBoards",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Job boards",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/JobBoardsResponse"
                },
                "example": {
                  "boards": [
                    {
                      "name": "indeed",
                      "title": "Indeed"
                    },
                    {
                      "name": "linkedin",
                      "title": "LinkedIn"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns current board publication state for a specific job. Useful for distribution dashboards and posting audits."
      },
      "post": {
        "tags": [
          "Jobs"
        ],
        "summary": "Activate boards for job",
        "operationId": "activateJobBoards",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobIdPath"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/JobBoardsMutationRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Job boards",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/JobBoardsResponse"
                },
                "example": {
                  "boards": [
                    {
                      "name": "indeed",
                      "title": "Indeed"
                    },
                    {
                      "name": "linkedin",
                      "title": "LinkedIn"
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Sets selected job boards to activation queue state. Use for controlled multi-board publishing workflows."
      },
      "delete": {
        "tags": [
          "Jobs"
        ],
        "summary": "Deactivate boards for job",
        "operationId": "deactivateJobBoards",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/JobBoardsMutationRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Job boards",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/JobBoardsResponse"
                },
                "example": {
                  "boards": [
                    {
                      "name": "indeed",
                      "title": "Indeed"
                    },
                    {
                      "name": "linkedin",
                      "title": "LinkedIn"
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Stops selected board publications for a job."
      }
    },
    "/jobs/batch-job-boards": {
      "get": {
        "tags": [
          "Jobs"
        ],
        "summary": "Get boards state for multiple jobs",
        "operationId": "batchGetJobBoards",
        "parameters": [
          {
            "$ref": "#/components/parameters/JobsQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Job boards by jobs",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchJobBoardsResponse"
                },
                "example": {
                  "jobs": [
                    {
                      "job_id": 10,
                      "boards": [
                        {
                          "name": "indeed",
                          "title": "Indeed"
                        },
                        {
                          "name": "linkedin",
                          "title": "LinkedIn"
                        }
                      ]
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns board states for multiple jobs in one request. Optimized for batch monitoring and management UIs."
      },
      "post": {
        "tags": [
          "Jobs"
        ],
        "summary": "Activate boards for multiple jobs",
        "operationId": "batchActivateJobBoards",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchJobBoardsRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Job boards by jobs",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchJobBoardsResponse"
                },
                "example": {
                  "jobs": [
                    {
                      "job_id": 10,
                      "boards": [
                        {
                          "name": "indeed",
                          "title": "Indeed"
                        },
                        {
                          "name": "linkedin",
                          "title": "LinkedIn"
                        }
                      ]
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Activates board publication for multiple jobs in one request."
      },
      "delete": {
        "tags": [
          "Jobs"
        ],
        "summary": "Deactivate boards for multiple jobs",
        "operationId": "batchDeactivateJobBoards",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BatchJobBoardsRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Job boards by jobs",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BatchJobBoardsResponse"
                },
                "example": {
                  "jobs": [
                    {
                      "job_id": 10,
                      "boards": [
                        {
                          "name": "indeed",
                          "title": "Indeed"
                        },
                        {
                          "name": "linkedin",
                          "title": "LinkedIn"
                        }
                      ]
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Deactivates board publication for multiple jobs in one request."
      }
    },
    "/companies": {
      "get": {
        "tags": [
          "Companies"
        ],
        "summary": "List partner companies",
        "operationId": "listCompanies",
        "parameters": [
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Company list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CompanyListResponse"
                },
                "example": {
                  "companies": [
                    {
                      "id": 101,
                      "name": "Acme Corp",
                      "website": "https://acme.com",
                      "url": "https://app.100hires.com/acme",
                      "is_staffing_agency": false,
                      "logo": "https://cdn.100hires.com/logos/acme.png",
                      "company_owner_email": "owner@acme.com",
                      "company_owner_phone": "+1-555-0100",
                      "company_owner_name": "John Doe"
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns partner-accessible companies with pagination metadata. Use for tenant discovery and management panels."
      },
      "post": {
        "tags": [
          "Companies"
        ],
        "summary": "Create company",
        "operationId": "createCompany",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CompanyCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created company",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Company"
                },
                "example": {
                  "id": 102,
                  "name": "Acme Corp",
                  "website": "https://acme.com",
                  "url": "https://app.100hires.com/acme",
                  "is_staffing_agency": false,
                  "logo": null,
                  "company_owner_email": "owner@acme.com",
                  "company_owner_phone": "+1-555-0100",
                  "company_owner_name": "John Doe"
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Creates a client company and links ownership context according to partner rules. Typical entrypoint for multi-tenant onboarding."
      }
    },
    "/companies/{id}": {
      "get": {
        "tags": [
          "Companies"
        ],
        "summary": "Get company",
        "operationId": "getCompany",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Company",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Company"
                },
                "example": {
                  "id": 101,
                  "name": "Acme Corp",
                  "website": "https://acme.com",
                  "url": "https://app.100hires.com/acme",
                  "is_staffing_agency": false,
                  "logo": "https://cdn.100hires.com/logos/acme.png",
                  "company_owner_email": "owner@acme.com",
                  "company_owner_phone": "+1-555-0100",
                  "company_owner_name": "John Doe"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns company profile and owner metadata used by partner APIs. Use before updates or ownership-sensitive actions."
      },
      "put": {
        "tags": [
          "Companies"
        ],
        "summary": "Update company",
        "operationId": "updateCompany",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CompanyUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated company",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Company"
                },
                "example": {
                  "id": 101,
                  "name": "Acme Corp Updated",
                  "website": "https://acme.com",
                  "url": "https://app.100hires.com/acme",
                  "is_staffing_agency": false,
                  "logo": "https://cdn.100hires.com/logos/acme.png",
                  "company_owner_email": "owner@acme.com",
                  "company_owner_phone": "+1-555-0200",
                  "company_owner_name": "John Doe"
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Updates company profile, owner contact data, and optional logo payload. Supports partner-operated account management flows."
      },
      "delete": {
        "tags": [
          "Companies"
        ],
        "summary": "Delete company",
        "operationId": "deleteCompany",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes a company. Use for lifecycle control in partner tenancy management."
      }
    },
    "/companies/{id}/restore": {
      "patch": {
        "tags": [
          "Companies"
        ],
        "summary": "Restore company",
        "operationId": "restoreCompany",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Restored company",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Company"
                },
                "example": {
                  "id": 101,
                  "name": "Acme Corp",
                  "website": "https://acme.com",
                  "url": "https://app.100hires.com/acme",
                  "is_staffing_agency": false,
                  "logo": "https://cdn.100hires.com/logos/acme.png",
                  "company_owner_email": "owner@acme.com",
                  "company_owner_phone": "+1-555-0100",
                  "company_owner_name": "John Doe"
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Restores a previously deleted company and re-enables it for active use. Use for recovery and rollback scenarios."
      }
    },
    "/companies/{id}/webhooks": {
      "get": {
        "tags": [
          "Companies"
        ],
        "summary": "List company webhooks",
        "operationId": "listCompanyWebhooks",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Company webhooks",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookListResponse"
                },
                "example": {
                  "webhooks": [
                    {
                      "id": 501,
                      "url": "https://hooks.example.com/100hires"
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Lists webhook subscriptions configured at company scope."
      },
      "post": {
        "tags": [
          "Companies"
        ],
        "summary": "Create company webhook",
        "operationId": "createCompanyWebhook",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/WebhookCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created webhook. `signing_secret` is returned only here — store it securely.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookWithSecret"
                },
                "example": {
                  "id": 502,
                  "url": "https://hooks.example.com/100hires",
                  "signing_secret": "3f9a8b7c6d5e4f0a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b0c1d2e3f4a"
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Creates a company-scoped webhook subscription. Use for outbound company-level event integrations."
      }
    },
    "/companies/{id}/webhooks/{webhook_id}/rotate-secret": {
      "post": {
        "tags": [
          "Companies"
        ],
        "summary": "Rotate company webhook signing secret",
        "operationId": "rotateCompanyWebhookSecret",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/WebhookIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "New signing secret (the previous one stays valid for a grace window).",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookWithSecret"
                },
                "example": {
                  "id": 502,
                  "url": "https://hooks.example.com/100hires",
                  "signing_secret": "9b0c1d2e3f4a5b6c7d8e9f0a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b0c"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Rotates the webhook's signing secret with zero downtime. The previous secret remains valid for a grace window so both old and new `x-hires-signature-v2` signatures are accepted while you switch over."
      }
    },
    "/companies/{id}/webhooks/{webhook_id}": {
      "delete": {
        "tags": [
          "Companies"
        ],
        "summary": "Delete company webhook",
        "operationId": "deleteCompanyWebhook",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/WebhookIdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes a company-scoped webhook subscription by ID. Use for endpoint retirement and security rotation."
      }
    },
    "/companies/mail-accounts": {
      "get": {
        "tags": [
          "Companies"
        ],
        "summary": "List all mail accounts for current company",
        "operationId": "listCompanyMailAccounts",
        "parameters": [
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Company mail accounts",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CompanyMailAccountListResponse"
                },
                "example": {
                  "mail_accounts": [
                    {
                      "id": 301,
                      "company_id": 101,
                      "user_id": 1,
                      "user_email": "recruiter@acme.com",
                      "email": "hiring@acme.com",
                      "provider": {
                        "name": "gmail",
                        "label": "Gmail"
                      },
                      "mailbox_id": 10,
                      "is_default": true,
                      "is_configured": true
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns all mail accounts for all users in the current company. Use this to resolve `from_account_id` before creating scheduled emails."
      }
    },
    "/companies/{id}/mail-accounts": {
      "get": {
        "tags": [
          "Companies"
        ],
        "summary": "List all mail accounts for a company",
        "operationId": "listCompanyMailAccountsById",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Company mail accounts",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CompanyMailAccountListResponse"
                },
                "example": {
                  "mail_accounts": [
                    {
                      "id": 301,
                      "company_id": 101,
                      "user_id": 1,
                      "user_email": "recruiter@acme.com",
                      "email": "hiring@acme.com",
                      "provider": {
                        "name": "gmail",
                        "label": "Gmail"
                      },
                      "mailbox_id": 10,
                      "is_default": true,
                      "is_configured": true
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns all mail accounts for all users in the specified company. The company must be accessible (own company or a client)."
      }
    },
    "/notes": {
      "get": {
        "tags": [
          "Notes"
        ],
        "summary": "List notes by candidate",
        "operationId": "listNotes",
        "parameters": [
          {
            "name": "candidate_id",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "pattern": "^[A-Za-z0-9_-]+$"
            },
            "description": "Candidate ID (numeric) or alias"
          },
          {
            "$ref": "#/components/parameters/NoteIncludeQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Note list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/NoteListResponse"
                },
                "example": {
                  "notes": [
                    {
                      "id": 67890,
                      "candidate_id": 12345,
                      "user_id": 1,
                      "body": "Strong technical background, moving to next round.",
                      "visibility": "all",
                      "created_at": 1711036800,
                      "updated_at": 1711036800
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated discussion notes for a candidate. Use for shared recruiter context and timeline synchronization."
      },
      "post": {
        "tags": [
          "Notes"
        ],
        "summary": "Create note",
        "operationId": "createNote",
        "parameters": [
          {
            "$ref": "#/components/parameters/NoteIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/NoteCreateRequest"
              },
              "example": {
                "candidate_id": 12345,
                "body": "Hey @Alice Smith, please review this candidate.",
                "visibility": "all",
                "mention_user_ids": [
                  42
                ]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created note",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Note"
                },
                "example": {
                  "id": 67890,
                  "candidate_id": 12345,
                  "user_id": 1,
                  "body": "Hey <span class=\"mention-area\" contenteditable=\"false\"><span class=\"highlight\"><span class=\"mentiony-link\">Alice Smith</span></span></span>, please review this candidate.",
                  "visibility": "all",
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Creates a new discussion note for a candidate. Supports visibility control (all or private) and @mentions with email notifications."
      }
    },
    "/notes/{id}": {
      "get": {
        "tags": [
          "Notes"
        ],
        "summary": "Get note",
        "operationId": "getNote",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/NoteIncludeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Note",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Note"
                },
                "example": {
                  "id": 67890,
                  "candidate_id": 12345,
                  "user_id": 1,
                  "body": "Strong technical background, moving to next round.",
                  "visibility": "all",
                  "created_at": 1711036800,
                  "updated_at": 1711036800,
                  "user": {
                    "id": 1,
                    "full_name": "Alice Smith",
                    "photo": "https://cdn.100hires.com/photos/alice.jpg"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns a single note with author and visibility metadata. Use `include=user` to load author details, `include=candidate` to embed the full candidate payload (with `url_backoffice`)."
      },
      "put": {
        "tags": [
          "Notes"
        ],
        "summary": "Update note",
        "operationId": "updateNote",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/NoteIncludeQuery"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/NoteUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated note",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Note"
                },
                "example": {
                  "id": 67890,
                  "candidate_id": 12345,
                  "user_id": 1,
                  "body": "Updated: Strong technical background, scheduled final interview.",
                  "visibility": "all",
                  "created_at": 1711036800,
                  "updated_at": 1711123200
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Updates note body and/or visibility without creating a new timeline item. Use for corrections and moderation workflows."
      },
      "delete": {
        "tags": [
          "Notes"
        ],
        "summary": "Delete note",
        "operationId": "deleteNote",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes a note from active collaboration views. Use for moderation policies and data cleanup operations."
      }
    },
    "/forms": {
      "get": {
        "tags": [
          "Forms"
        ],
        "summary": "List forms",
        "operationId": "listForms",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Form list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/FormListResponse"
                },
                "example": {
                  "forms": [
                    {
                      "id": 10,
                      "name": "Software Engineer Application",
                      "questions": [
                        {
                          "id": 201,
                          "text": "Years of experience?",
                          "type": "short_text",
                          "options": [

                          ],
                          "status": "required"
                        }
                      ]
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated application forms for the target company. Use to bootstrap questionnaire builders and sync form catalogs."
      },
      "post": {
        "tags": [
          "Forms"
        ],
        "summary": "Create form",
        "operationId": "createForm",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/FormCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created form",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Form"
                },
                "example": {
                  "id": 11,
                  "name": "Designer Application",
                  "questions": [

                  ]
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Creates a new form and optionally attaches existing questions. Useful for standardized intake process setup."
      }
    },
    "/forms/{id}": {
      "get": {
        "tags": [
          "Forms"
        ],
        "summary": "Get form",
        "operationId": "getForm",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Form",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Form"
                },
                "example": {
                  "id": 10,
                  "name": "Software Engineer Application",
                  "url_backoffice": "https://app.100hires.com/settings/forms/10/edit",
                  "questions": [
                    {
                      "id": 201,
                      "text": "Years of experience?",
                      "type": "short_text",
                      "status": "required"
                    },
                    {
                      "id": 202,
                      "text": "Preferred programming language?",
                      "type": "single_choice",
                      "options": [
                        "Python",
                        "Java",
                        "Go",
                        "TypeScript"
                      ],
                      "status": "optional"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns form details with included question statuses. Use as canonical read endpoint for form rendering."
      },
      "put": {
        "tags": [
          "Forms"
        ],
        "summary": "Update form",
        "operationId": "updateForm",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/FormUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated form",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Form"
                },
                "example": {
                  "id": 10,
                  "name": "Software Engineer Application",
                  "url_backoffice": "https://app.100hires.com/settings/forms/10/edit",
                  "questions": [
                    {
                      "id": 201,
                      "text": "Years of experience?",
                      "type": "short_text",
                      "status": "required"
                    },
                    {
                      "id": 202,
                      "text": "Preferred programming language?",
                      "type": "single_choice",
                      "options": [
                        "Python",
                        "Java",
                        "Go",
                        "TypeScript"
                      ],
                      "status": "optional"
                    }
                  ]
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Updates form metadata and question composition. Supports iterative form design and rollout workflows."
      },
      "delete": {
        "tags": [
          "Forms"
        ],
        "summary": "Delete form",
        "operationId": "deleteForm",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes a form from active usage. Use when retiring obsolete intake flows."
      }
    },
    "/forms/{form_id}/questions/{question_id}": {
      "put": {
        "tags": [
          "Forms"
        ],
        "summary": "Update question status inside form",
        "operationId": "updateFormQuestionStatus",
        "parameters": [
          {
            "$ref": "#/components/parameters/FormIdPath"
          },
          {
            "$ref": "#/components/parameters/QuestionIdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/FormQuestionStatusRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated form",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Form"
                },
                "example": {
                  "id": 10,
                  "name": "Software Engineer Application",
                  "url_backoffice": "https://app.100hires.com/settings/forms/10/edit",
                  "questions": [
                    {
                      "id": 201,
                      "text": "Years of experience?",
                      "type": "short_text",
                      "status": "required"
                    },
                    {
                      "id": 202,
                      "text": "Preferred programming language?",
                      "type": "single_choice",
                      "options": [
                        "Python",
                        "Java",
                        "Go",
                        "TypeScript"
                      ],
                      "status": "optional"
                    }
                  ]
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Changes the status (required/optional/hidden) of a form-question relation. Use for fine-grained validation control."
      }
    },
    "/questions": {
      "get": {
        "tags": [
          "Questions"
        ],
        "summary": "List questions",
        "operationId": "listQuestions",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Question list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/QuestionListResponse"
                },
                "example": {
                  "questions": [
                    {
                      "id": 201,
                      "text": "Years of experience?",
                      "type": "short_text"
                    },
                    {
                      "id": 202,
                      "text": "Preferred programming language?",
                      "type": "single_choice",
                      "options": [
                        "Python",
                        "Java",
                        "Go",
                        "TypeScript"
                      ]
                    }
                  ],
                  "pagination": {
                    "page_size": 20,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 2
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated question catalog for the target company."
      },
      "post": {
        "tags": [
          "Questions"
        ],
        "summary": "Create question",
        "operationId": "createQuestion",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/QuestionCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created question",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Question"
                },
                "example": {
                  "id": 203,
                  "text": "Years of experience?",
                  "type": "short_text"
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Creates a reusable question definition with optional options for dropdown types. Used by forms and questionnaires."
      }
    },
    "/questions/{id}": {
      "get": {
        "tags": [
          "Questions"
        ],
        "summary": "Get question",
        "operationId": "getQuestion",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Question",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Question"
                },
                "example": {
                  "id": 202,
                  "text": "Preferred programming language?",
                  "type": "single_choice",
                  "options": [
                    "Python",
                    "Java",
                    "Go",
                    "TypeScript"
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns question definition including type and options. Use for editors, validators, and sync clients."
      },
      "put": {
        "tags": [
          "Questions"
        ],
        "summary": "Update question",
        "operationId": "updateQuestion",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/QuestionUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated question",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Question"
                },
                "example": {
                  "id": 202,
                  "text": "Preferred programming language?",
                  "type": "single_choice",
                  "options": [
                    "Python",
                    "Java",
                    "Go",
                    "TypeScript",
                    "Rust"
                  ]
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Updates text/type/options of an existing question definition. Supports schema evolution of assessment content."
      },
      "delete": {
        "tags": [
          "Questions"
        ],
        "summary": "Delete question",
        "operationId": "deleteQuestion",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Deletes a reusable question from the catalog. Use cautiously when deprecating question banks."
      }
    },
    "/questions/types": {
      "get": {
        "tags": [
          "Questions"
        ],
        "summary": "List available question types",
        "operationId": "listQuestionTypes",
        "responses": {
          "200": {
            "description": "Question types",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/QuestionTypesResponse"
                },
                "example": {
                  "types": [
                    "short_text",
                    "long_text",
                    "single_choice",
                    "multiple_choice",
                    "file_upload",
                    "score_card",
                    "number",
                    "boolean",
                    "date",
                    "time",
                    "email",
                    "phone"
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns available question types supported by the platform. Use this endpoint to drive dynamic form builders."
      }
    },
    "/users": {
      "get": {
        "tags": [
          "Users"
        ],
        "summary": "List users",
        "operationId": "listUsers",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "User list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/UserListResponse"
                },
                "example": {
                  "users": [
                    {
                      "id": 1,
                      "full_name": "Alice Smith",
                      "email": "alice@acme.com",
                      "role": "admin",
                      "default_mail_account_id": 301,
                      "created_at": 1711036800,
                      "updated_at": 1711036800
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated users for the target company with role context. Useful for access reviews and hiring-team management."
      }
    },
    "/users/{id}": {
      "get": {
        "tags": [
          "Users"
        ],
        "summary": "Get user",
        "operationId": "getUser",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "User",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/User"
                },
                "example": {
                  "id": 1,
                  "full_name": "Alice Smith",
                  "email": "alice@acme.com",
                  "role": "admin",
                  "default_mail_account_id": 301,
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns a single user accessible in current tenant scope. Use for identity resolution in automation flows."
      }
    },
    "/users/{id}/mail-accounts": {
      "get": {
        "tags": [
          "Users"
        ],
        "summary": "List user's mail accounts",
        "operationId": "listUserMailAccounts",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "User mail accounts",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/MailAccountListResponse"
                },
                "example": {
                  "mail_accounts": [
                    {
                      "id": 301,
                      "email": "alice@acme.com",
                      "provider": {
                        "name": "gmail",
                        "label": "Gmail"
                      },
                      "mailbox_id": 10,
                      "is_default": true,
                      "is_configured": true
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns mail accounts connected to the specified user within the current tenant scope. Use this endpoint to resolve `from_account_id` before creating scheduled emails."
      }
    },
    "/tags": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List company tags",
        "operationId": "listTags",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Tags",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TagListResponse"
                },
                "example": {
                  "tags": [
                    "Senior",
                    "Remote",
                    "Urgent"
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 3
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns all tags available for the target company. Recommended to cache for fast tagging UX and validation."
      }
    },
    "/email-templates": {
      "get": {
        "tags": [
          "Email Templates"
        ],
        "summary": "List email templates",
        "operationId": "listEmailTemplates",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          },
          {
            "$ref": "#/components/parameters/ViewQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Email template list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EmailTemplateListResponse"
                },
                "example": {
                  "email_templates": [
                    {
                      "id": 401,
                      "name": "Interview Invitation",
                      "subject": "Interview invitation",
                      "body": "<p>Hi <tag contenteditable=\"false\" data-type=\"system\" data-identifier=\"first_name\">First Name</tag>, we'd like to invite you for an interview.</p>",
                      "created_at": 1711036800,
                      "updated_at": 1711036800
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated email templates for the target company."
      },
      "post": {
        "tags": [
          "Email Templates"
        ],
        "summary": "Create email template",
        "operationId": "createEmailTemplate",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/EmailTemplateCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created email template",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EmailTemplate"
                },
                "example": {
                  "id": 402,
                  "name": "Rejection Letter",
                  "subject": "Update on your application",
                  "body": "<p>Dear <tag contenteditable=\"false\" data-type=\"system\" data-identifier=\"first_name\">First Name</tag>, thank you for your interest.</p>",
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Creates a new email template with subject and body.\n\n**Placeholder workflow:**\n1. `GET /template-placeholders` — list available placeholders\n2. `POST /template-placeholders/prepare` — convert chosen placeholder to an HTML `<tag>` element\n3. Insert the returned HTML tag into the template body\n4. `POST /email-templates` — save the template with embedded placeholder tags\n"
      }
    },
    "/email-templates/{id}": {
      "get": {
        "tags": [
          "Email Templates"
        ],
        "summary": "Get email template",
        "operationId": "getEmailTemplate",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Email template",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EmailTemplate"
                },
                "example": {
                  "id": 401,
                  "name": "Interview Invitation",
                  "subject": "Interview invitation",
                  "body": "<p>Hi <tag contenteditable=\"false\" data-type=\"system\" data-identifier=\"first_name\">First Name</tag>, we'd like to invite you for an interview.</p>",
                  "created_at": 1711036800,
                  "updated_at": 1711036800
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns a single email template by ID with subject and body content."
      },
      "put": {
        "tags": [
          "Email Templates"
        ],
        "summary": "Update email template",
        "operationId": "updateEmailTemplate",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/EmailTemplateUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated email template",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EmailTemplate"
                },
                "example": {
                  "id": 401,
                  "name": "Interview Invitation v2",
                  "subject": "Interview invitation",
                  "body": "<p>Hi <tag contenteditable=\"false\" data-type=\"system\" data-identifier=\"first_name\">First Name</tag>, we'd love to schedule an interview with you.</p>",
                  "created_at": 1711036800,
                  "updated_at": 1711123200
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Updates an existing email template. Only provided fields are overwritten; omitted fields keep their current values.\n\nTo add placeholders to the body, use the same workflow as for creation:\n1. `GET /template-placeholders` — list available placeholders\n2. `POST /template-placeholders/prepare` — get HTML tag for the chosen placeholder\n3. Insert the tag into the body and `PUT /email-templates/{id}`\n"
      },
      "delete": {
        "tags": [
          "Email Templates"
        ],
        "summary": "Delete email template",
        "operationId": "deleteEmailTemplate",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Soft-deletes an email template. Templates already used in automations will stop being available for new actions."
      }
    },
    "/template-placeholders": {
      "get": {
        "tags": [
          "Template Placeholders"
        ],
        "summary": "List available placeholders",
        "operationId": "listTemplatePlaceholders",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "name": "type",
            "in": "query",
            "description": "Filter by placeholder type: profile_field, job_variable, questionnaire_link, self_scheduling_link",
            "schema": {
              "type": "string",
              "enum": [
                "profile_field",
                "job_variable",
                "questionnaire_link",
                "self_scheduling_link"
              ]
            }
          },
          {
            "name": "is_notification",
            "in": "query",
            "description": "Include notification-specific system placeholders",
            "schema": {
              "type": "integer",
              "enum": [
                0,
                1
              ],
              "default": 0
            }
          },
          {
            "name": "q",
            "in": "query",
            "description": "Filter placeholders by label (case-insensitive substring match)",
            "schema": {
              "type": "string"
            }
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Placeholder list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TemplatePlaceholderListResponse"
                },
                "example": {
                  "placeholders": [
                    {
                      "type": "system",
                      "identifier": "first_name",
                      "label": "First Name",
                      "is_link": false,
                      "is_job_variable": false
                    },
                    {
                      "type": "job_variable",
                      "identifier": "job_title",
                      "label": "Job Title",
                      "is_link": false,
                      "is_job_variable": true,
                      "job_variable_id": 5
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 2
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns available placeholders for email templates with pagination.\n\n**Workflow:** Use this endpoint to discover placeholders, then call `POST /template-placeholders/prepare` with the chosen placeholder to get an HTML tag. Insert that tag into the email template body.\n\nUse `type` to filter by category, `q` to search by label.\n"
      }
    },
    "/template-placeholders/prepare": {
      "post": {
        "tags": [
          "Template Placeholders"
        ],
        "summary": "Prepare placeholder tag",
        "operationId": "prepareTemplatePlaceholder",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/PreparePlaceholderRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Prepared placeholder HTML tag",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "html": {
                      "type": "string",
                      "description": "HTML tag string for embedding in template body"
                    }
                  }
                },
                "example": {
                  "html": "<tag contenteditable=\"false\" data-type=\"system\" data-identifier=\"first_name\">First Name</tag>"
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Converts a placeholder reference into an HTML tag that can be inserted into an email template body."
      }
    },
    "/nurture-campaigns": {
      "get": {
        "tags": [
          "Nurture Campaigns"
        ],
        "summary": "List nurture campaigns",
        "operationId": "listNurtureCampaigns",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Nurture campaign list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/NurtureCampaignListResponse"
                },
                "example": {
                  "nurture_campaigns": [
                    {
                      "id": 601,
                      "type": "nurture_campaign",
                      "title": "Follow-up Sequence",
                      "send_to_all": false,
                      "response_move_to_stage_id": null,
                      "schedule": {
                        "formatted": "Mon-Fri, 9am-5pm"
                      },
                      "steps": [
                        {
                          "id": 1001,
                          "type": "email",
                          "campaign_id": 601,
                          "delay_days": 0,
                          "send_condition": "if_no_reply",
                          "sender": {
                            "type": "user",
                            "id": 1
                          },
                          "template_id": 401,
                          "is_new_thread": true,
                          "schedule_id": null
                        }
                      ]
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns paginated nurture campaigns for the target company."
      },
      "post": {
        "tags": [
          "Nurture Campaigns"
        ],
        "summary": "Create nurture campaign",
        "operationId": "createNurtureCampaign",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/NurtureCampaignCreateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Created nurture campaign",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/NurtureCampaign"
                },
                "example": {
                  "id": 602,
                  "type": "nurture_campaign",
                  "title": "New Candidate Outreach",
                  "send_to_all": true,
                  "response_move_to_stage_id": 50,
                  "schedule": {
                    "formatted": "Mon-Fri, 9am-5pm"
                  },
                  "steps": [
                    {
                      "id": 1002,
                      "type": "email",
                      "campaign_id": 602,
                      "delay_days": 0,
                      "send_condition": "if_no_reply",
                      "sender": {
                        "type": "user",
                        "id": 1
                      },
                      "template_id": 401,
                      "is_new_thread": true,
                      "schedule_id": null
                    },
                    {
                      "id": 1003,
                      "type": "email",
                      "campaign_id": 602,
                      "delay_days": 3,
                      "send_condition": "if_no_reply",
                      "sender": {
                        "type": "user",
                        "id": 1
                      },
                      "template_id": 402,
                      "is_new_thread": false,
                      "schedule_id": null
                    }
                  ]
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Creates a new nurture campaign with steps. Optionally bind to a workflow stage via workflow_id and stage_id."
      }
    },
    "/nurture-campaigns/{id}": {
      "get": {
        "tags": [
          "Nurture Campaigns"
        ],
        "summary": "Get nurture campaign",
        "operationId": "getNurtureCampaign",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Nurture campaign",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/NurtureCampaign"
                },
                "example": {
                  "id": 601,
                  "type": "nurture_campaign",
                  "title": "Follow-up Sequence",
                  "send_to_all": false,
                  "response_move_to_stage_id": null,
                  "schedule": {
                    "formatted": "Mon-Fri, 9am-5pm"
                  },
                  "steps": [
                    {
                      "id": 1001,
                      "type": "email",
                      "campaign_id": 601,
                      "delay_days": 0,
                      "send_condition": "if_no_reply",
                      "sender": {
                        "type": "user",
                        "id": 1
                      },
                      "template_id": 401,
                      "is_new_thread": true,
                      "schedule_id": null
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns a single nurture campaign by ID with all steps."
      },
      "put": {
        "tags": [
          "Nurture Campaigns"
        ],
        "summary": "Update nurture campaign",
        "operationId": "updateNurtureCampaign",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/NurtureCampaignUpdateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Updated nurture campaign",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/NurtureCampaign"
                },
                "example": {
                  "id": 601,
                  "type": "nurture_campaign",
                  "title": "Follow-up Sequence v2",
                  "send_to_all": true,
                  "response_move_to_stage_id": 50,
                  "schedule": {
                    "formatted": "Mon-Fri, 9am-5pm"
                  },
                  "steps": [
                    {
                      "id": 1001,
                      "type": "email",
                      "campaign_id": 601,
                      "delay_days": 0,
                      "send_condition": "if_no_reply",
                      "sender": {
                        "type": "user",
                        "id": 1
                      },
                      "template_id": 401,
                      "is_new_thread": true,
                      "schedule_id": null
                    }
                  ]
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Updates an existing nurture campaign. Pass all steps — mark removed steps with is_deleted=true."
      },
      "delete": {
        "tags": [
          "Nurture Campaigns"
        ],
        "summary": "Delete nurture campaign",
        "operationId": "deleteNurtureCampaign",
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                },
                "example": {
                  "success": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Soft-deletes a nurture campaign. Active campaign executions will be stopped."
      }
    },
    "/workflows": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List workflows",
        "operationId": "listWorkflows",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Workflows",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WorkflowListResponse"
                },
                "example": {
                  "workflows": [
                    {
                      "id": 1,
                      "name": "Default Pipeline",
                      "stages": [
                        {
                          "id": 10,
                          "name": "Applied",
                          "order": 1
                        },
                        {
                          "id": 11,
                          "name": "Interview",
                          "order": 2
                        },
                        {
                          "id": 12,
                          "name": "Offer",
                          "order": 3
                        }
                      ]
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns workflows and embedded stages for the target company. Use to build stage-aware integrations and routing rules."
      }
    },
    "/workflows/stages": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List workflow stages",
        "operationId": "listWorkflowStages",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          },
          {
            "name": "workflow_id",
            "in": "query",
            "description": "Filter stages by workflow ID (from GET /taxonomy/workflows).",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "job_id",
            "in": "query",
            "description": "Filter stages by job ID (returns stages from the job's assigned workflow).",
            "schema": {
              "type": "integer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Stages",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WorkflowStagesResponse"
                },
                "example": {
                  "stages": [
                    {
                      "id": 10,
                      "name": "Applied",
                      "order": 1
                    },
                    {
                      "id": 11,
                      "name": "Interview",
                      "order": 2
                    },
                    {
                      "id": 12,
                      "name": "Offer",
                      "order": 3
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns pipeline stages filtered by workflow or job when provided. Useful for transition UIs and workflow validation."
      }
    },
    "/workflows/{id}/stages": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List stages for a specific workflow",
        "operationId": "listWorkflowStagesById",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Workflow ID",
            "schema": {
              "type": "integer"
            }
          },
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Stages for the specified workflow",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WorkflowStagesResponse"
                },
                "example": {
                  "stages": [
                    {
                      "id": 10,
                      "name": "Applied",
                      "order": 1
                    },
                    {
                      "id": 11,
                      "name": "Interview",
                      "order": 2
                    },
                    {
                      "id": 12,
                      "name": "Offer",
                      "order": 3
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns stages for a specific workflow by ID. Equivalent to `GET /workflows/stages?workflow_id={id}`."
      }
    },
    "/statuses": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List statuses",
        "operationId": "listStatuses",
        "responses": {
          "200": {
            "description": "Statuses",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/StatusesResponse"
                },
                "example": {
                  "statuses": [
                    "draft",
                    "published",
                    "on_hold",
                    "closed",
                    "archived"
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns job status labels used by the platform. Cache this taxonomy to validate job status updates."
      }
    },
    "/categories": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List categories",
        "operationId": "listCategories",
        "responses": {
          "200": {
            "description": "Categories",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CategoriesResponse"
                },
                "example": {
                  "categories": [
                    {
                      "id": 1,
                      "name": "Engineering"
                    },
                    {
                      "id": 2,
                      "name": "Design"
                    },
                    {
                      "id": 3,
                      "name": "Marketing"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns global job categories. Use for job classification and consistent taxonomy mapping."
      }
    },
    "/employment-types": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List employment types",
        "operationId": "listEmploymentTypes",
        "responses": {
          "200": {
            "description": "Employment types",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EmploymentTypesResponse"
                },
                "example": {
                  "employment_types": [
                    {
                      "id": 1,
                      "name": "Full-time"
                    },
                    {
                      "id": 2,
                      "name": "Part-time"
                    },
                    {
                      "id": 3,
                      "name": "Contract"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns supported employment types. Use for validation and external system normalization."
      }
    },
    "/education-levels": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List education levels",
        "operationId": "listEducationLevels",
        "responses": {
          "200": {
            "description": "Education levels",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EducationLevelsResponse"
                },
                "example": {
                  "education_levels": [
                    {
                      "id": 1,
                      "name": "High School"
                    },
                    {
                      "id": 2,
                      "name": "Bachelor's"
                    },
                    {
                      "id": 3,
                      "name": "Master's"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns education level taxonomy values. Useful for job requirements and structured matching."
      }
    },
    "/experience-levels": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List experience levels",
        "operationId": "listExperienceLevels",
        "responses": {
          "200": {
            "description": "Experience levels",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ExperienceLevelsResponse"
                },
                "example": {
                  "experience_levels": [
                    {
                      "id": 1,
                      "name": "Entry Level"
                    },
                    {
                      "id": 2,
                      "name": "Mid Level"
                    },
                    {
                      "id": 3,
                      "name": "Senior"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns experience level taxonomy values for role seniority modeling."
      }
    },
    "/origins": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List origins",
        "operationId": "listOrigins",
        "responses": {
          "200": {
            "description": "Origins",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/OriginsResponse"
                },
                "example": {
                  "origins": [
                    {
                      "id": 1,
                      "name": "Applied"
                    },
                    {
                      "id": 2,
                      "name": "Sourced"
                    },
                    {
                      "id": 3,
                      "name": "Referred"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns candidate origin taxonomy values. Use for attribution analytics and source normalization."
      }
    },
    "/sources": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List sources",
        "operationId": "listSources",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Sources",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SourcesResponse"
                },
                "example": {
                  "sources": [
                    {
                      "id": 1,
                      "name": "LinkedIn"
                    },
                    {
                      "id": 2,
                      "name": "Indeed"
                    },
                    {
                      "id": 3,
                      "name": "Company Website"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns company-specific source list. Recommended for attribution sync and reporting consistency."
      }
    },
    "/boards": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List boards",
        "operationId": "listBoards",
        "responses": {
          "200": {
            "description": "Boards",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BoardsResponse"
                },
                "example": {
                  "boards": [
                    {
                      "name": "indeed",
                      "title": "Indeed"
                    },
                    {
                      "name": "linkedin",
                      "title": "LinkedIn"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns available publishing boards with board metadata. Use for distribution setup and board selection UIs."
      }
    },
    "/rejection-reasons": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List rejection reasons",
        "operationId": "listRejectionReasons",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Rejection reasons",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RejectionReasonsResponse"
                },
                "example": {
                  "rejection_reasons": [
                    {
                      "id": 1,
                      "name": "Not enough experience"
                    },
                    {
                      "id": 2,
                      "name": "Position filled"
                    },
                    {
                      "id": 3,
                      "name": "Salary expectations too high"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns configured rejection reasons for the target company. Use to validate rejection actions and analytics."
      }
    },
    "/departments": {
      "get": {
        "tags": [
          "Taxonomy"
        ],
        "summary": "List departments",
        "operationId": "listDepartments",
        "parameters": [
          {
            "$ref": "#/components/parameters/CompanyIdQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Departments",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DepartmentsResponse"
                },
                "example": {
                  "departments": [
                    {
                      "id": 1,
                      "name": "Engineering"
                    },
                    {
                      "id": 2,
                      "name": "Product"
                    },
                    {
                      "id": 3,
                      "name": "Sales"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns departments for the target company. Use for job organization filters and reporting dimensions."
      }
    },
    "/billing": {
      "get": {
        "tags": [
          "Billing"
        ],
        "summary": "Billing/pricing flags for current company",
        "operationId": "getBillingFlags",
        "responses": {
          "200": {
            "description": "Billing state",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/BillingResponse"
                },
                "example": {
                  "success": true,
                  "is_pricing_enabled": true,
                  "is_paid": true
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns pricing/billing capability flags for the current company context. Use before invoking paid-only API behaviors."
      }
    },
    "/career-site/jobs": {
      "get": {
        "tags": [
          "Career Site"
        ],
        "summary": "List public jobs",
        "operationId": "careerSiteListJobs",
        "security": [
          {
            "CompanySlugAuth": [

            ]
          }
        ],
        "parameters": [
          {
            "name": "company_slug",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "Company slug (alternative to X-Company-Slug header)"
          },
          {
            "name": "department_id",
            "in": "query",
            "required": false,
            "description": "Filter by department ID.",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "employment_type_id",
            "in": "query",
            "required": false,
            "description": "Filter by employment type ID (e.g. Full-time, Part-time).",
            "schema": {
              "type": "integer"
            }
          },
          {
            "name": "city",
            "in": "query",
            "required": false,
            "description": "Filter by job city (exact match).",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "country",
            "in": "query",
            "required": false,
            "description": "Filter by job country (exact match).",
            "schema": {
              "type": "string"
            }
          },
          {
            "$ref": "#/components/parameters/PageQuery"
          },
          {
            "$ref": "#/components/parameters/SizeQuery"
          }
        ],
        "responses": {
          "200": {
            "description": "Paginated list of public jobs",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CareerSiteJobListResponse"
                },
                "example": {
                  "jobs": [
                    {
                      "id": 5001,
                      "title": "Senior Software Engineer",
                      "description": "<p>We are looking for a senior engineer...</p>",
                      "department": {
                        "id": 1,
                        "name": "Engineering"
                      },
                      "location": {
                        "city": "San Francisco",
                        "country": "US",
                        "state": "CA"
                      },
                      "employment_type": {
                        "id": 1,
                        "name": "Full-time"
                      },
                      "is_remote": false,
                      "application_url": "https://acme.100hires.com/jobs/5001/apply",
                      "created_at": 1711036800
                    }
                  ],
                  "pagination": {
                    "page_size": 25,
                    "page_count": 1,
                    "page": 1,
                    "total_count": 1
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          }
        },
        "description": "Returns publicly visible jobs for the given company. Supports filtering by department, employment type, city, and country. Use to power a custom careers page."
      }
    },
    "/career-site/jobs/{id}": {
      "get": {
        "tags": [
          "Career Site"
        ],
        "summary": "Get public job",
        "operationId": "careerSiteGetJob",
        "security": [
          {
            "CompanySlugAuth": [

            ]
          }
        ],
        "parameters": [
          {
            "$ref": "#/components/parameters/IdPath"
          }
        ],
        "responses": {
          "200": {
            "description": "Job detail",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CareerSiteJobDetail"
                },
                "example": {
                  "id": 5001,
                  "title": "Senior Software Engineer",
                  "description": "<p>We are looking for a senior engineer to join our team.</p>",
                  "department": {
                    "id": 1,
                    "name": "Engineering"
                  },
                  "location": {
                    "city": "San Francisco",
                    "country": "US",
                    "state": "CA"
                  },
                  "employment_type": {
                    "id": 1,
                    "name": "Full-time"
                  },
                  "is_remote": false,
                  "application_url": "https://acme.100hires.com/jobs/5001/apply",
                  "created_at": 1711036800,
                  "salary_min": 120000,
                  "salary_max": 180000,
                  "salary_currency": "USD",
                  "salary_period": "annually",
                  "education_level": {
                    "id": 2,
                    "name": "Bachelor's"
                  },
                  "experience_level": {
                    "id": 3,
                    "name": "Senior"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          }
        },
        "description": "Returns full details for a single public or unlisted job. Returns 404 for draft, archived, or internal jobs."
      }
    },
    "/career-site/applications": {
      "post": {
        "tags": [
          "Career Site"
        ],
        "summary": "Submit job application",
        "operationId": "careerSiteCreateApplication",
        "security": [
          {
            "CompanySlugAuth": [

            ]
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CareerSiteApplicationRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Application created",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CareerSiteApplicationResponse"
                },
                "example": {
                  "id": 90001,
                  "job_id": 5001,
                  "status": "pending",
                  "created_at": 1711036800
                }
              }
            }
          },
          "415": {
            "$ref": "#/components/responses/UnsupportedMediaType"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "404": {
            "$ref": "#/components/responses/NotFound"
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          }
        },
        "description": "Submits a job application on behalf of a candidate. Creates a candidate record and triggers the career-site pipeline automation (sets stage to Applied, runs source attribution)."
      }
    },
    "/feedback": {
      "post": {
        "tags": [
          "Feedback"
        ],
        "summary": "Submit API feedback",
        "operationId": "createFeedback",
        "description": "Submit structured feedback about API usage, missing features, or workflow improvements.\nUseful for AI agents and integrations to report issues programmatically.\n\nRate limited to 5 requests per hour per account.\n",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "description"
                ],
                "properties": {
                  "description": {
                    "type": "string",
                    "maxLength": 2000,
                    "description": "Description of the issue or feedback",
                    "example": "For bulk candidate enrichment, need a batch lookup by email. Currently requires N+1 requests."
                  },
                  "endpoint": {
                    "type": "string",
                    "maxLength": 255,
                    "description": "The API endpoint this feedback relates to",
                    "example": "/v2/candidates"
                  },
                  "issue_type": {
                    "type": "string",
                    "enum": [
                      "missing_filter",
                      "pagination",
                      "performance",
                      "missing_field",
                      "bulk_operation",
                      "other"
                    ],
                    "description": "Category of the issue",
                    "example": "bulk_operation"
                  },
                  "suggested_improvement": {
                    "type": "string",
                    "maxLength": 2000,
                    "description": "Suggested solution or improvement",
                    "example": "Add POST /v2/candidates/search with array of emails in request body"
                  },
                  "context": {
                    "type": "object",
                    "description": "Arbitrary context object (max 4KB)",
                    "example": {
                      "agent": "claude",
                      "task_description": "Enriching 50 candidates from CSV",
                      "api_calls_made": 53,
                      "estimated_optimal_calls": 2
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Feedback received",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "success": {
                      "type": "boolean",
                      "example": true
                    },
                    "message": {
                      "type": "string",
                      "example": "Feedback received. Thank you!"
                    }
                  }
                },
                "example": {
                  "success": true,
                  "message": "Feedback received. Thank you!"
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/ValidationError"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "BearerAuth": {
        "type": "http",
        "scheme": "bearer",
        "bearerFormat": "APIKey",
        "description": "Provide API token in header: `Authorization: Bearer <token>`. Each key is scoped to a specific user + company pair."
      },
      "CompanySlugAuth": {
        "type": "apiKey",
        "in": "header",
        "name": "X-Company-Slug",
        "description": "Company slug for career site public endpoints. Alternative: pass as query param `company_slug`."
      }
    },
    "parameters": {
      "CompanyIdQuery": {
        "name": "company_id",
        "in": "query",
        "required": false,
        "schema": {
          "type": "integer"
        },
        "description": "Optional target company ID. Since each API key is already bound to one company, this is only needed when the key owner has access to multiple companies."
      },
      "ApplicationIncludeQuery": {
        "name": "include",
        "in": "query",
        "required": false,
        "schema": {
          "type": "string"
        },
        "description": "Comma-separated list of related resources to include. Supported: `candidate` — full candidate profile, `cv.text` — parsed plain-text CV content, `job` — full job payload with `url_backoffice` for UI deep-linking.",
        "style": "form",
        "explode": false
      },
      "CandidateIncludeQuery": {
        "name": "include",
        "in": "query",
        "required": false,
        "schema": {
          "type": "string",
          "enum": [
            "applications"
          ]
        },
        "description": "Include related application summaries in the candidate response."
      },
      "InterviewIncludeQuery": {
        "name": "include",
        "in": "query",
        "required": false,
        "schema": {
          "type": "string"
        },
        "description": "Comma-separated list of related resources to include. Supported: `candidate`, `application`, `job`.",
        "style": "form",
        "explode": false
      },
      "JobIncludeQuery": {
        "name": "include",
        "in": "query",
        "required": false,
        "schema": {
          "type": "string"
        },
        "description": "Comma-separated list of related resources to include. Supported: `workflow`, `hiring_team`, `pipeline_stages`.",
        "style": "form",
        "explode": false
      },
      "NoteIncludeQuery": {
        "name": "include",
        "in": "query",
        "required": false,
        "schema": {
          "type": "string"
        },
        "description": "Comma-separated list of related resources to include. Supported: `user` — author details, `candidate` — full candidate payload with `url_backoffice` for UI deep-linking.",
        "style": "form",
        "explode": false
      },
      "PageQuery": {
        "name": "page",
        "in": "query",
        "required": false,
        "description": "Page number (1-based). Defaults to 1.",
        "schema": {
          "type": "integer",
          "minimum": 1,
          "default": 1
        }
      },
      "SizeQuery": {
        "name": "size",
        "in": "query",
        "required": false,
        "description": "Number of items per page (1–100). Defaults to 20.",
        "schema": {
          "type": "integer",
          "minimum": 1,
          "maximum": 100,
          "default": 20
        }
      },
      "ViewQuery": {
        "name": "view",
        "in": "query",
        "required": false,
        "description": "Response shape selector for list endpoints. `full` (default) returns every field\n— backward-compatible with pre-existing clients. `summary` returns a thinned\npayload designed for agent-friendly list browsing: heavy fields (description\nHTML, embedded profile answers, full message bodies, embedded relations, etc.)\nare omitted or replaced with `*_preview` truncations. Use `summary` when paging\nthrough large result sets and fetch a single record with the corresponding\n`GET /{resource}/{id}` endpoint when full data is needed.\n",
        "schema": {
          "type": "string",
          "enum": [
            "full",
            "summary"
          ],
          "default": "full"
        }
      },
      "IdPath": {
        "name": "id",
        "in": "path",
        "required": true,
        "description": "Resource ID (numeric).",
        "schema": {
          "type": "integer"
        }
      },
      "CandidateIdPath": {
        "name": "id",
        "in": "path",
        "required": true,
        "schema": {
          "type": "string",
          "pattern": "^[A-Za-z0-9_-]+$"
        },
        "description": "Candidate ID (numeric) or alias"
      },
      "JobIdPath": {
        "name": "id",
        "in": "path",
        "required": true,
        "schema": {
          "type": "string",
          "pattern": "^[A-Za-z0-9_-]+$"
        },
        "description": "Job ID (numeric) or alias"
      },
      "WebhookIdPath": {
        "name": "webhook_id",
        "in": "path",
        "required": true,
        "description": "Webhook subscription ID.",
        "schema": {
          "type": "integer"
        }
      },
      "FormIdPath": {
        "name": "form_id",
        "in": "path",
        "required": true,
        "description": "Application form ID.",
        "schema": {
          "type": "integer"
        }
      },
      "QuestionIdPath": {
        "name": "question_id",
        "in": "path",
        "required": true,
        "description": "Question ID.",
        "schema": {
          "type": "integer"
        }
      },
      "TagPath": {
        "name": "tag",
        "in": "path",
        "required": true,
        "description": "Tag text (case-sensitive, URL-encoded).",
        "schema": {
          "type": "string"
        }
      },
      "JobsQuery": {
        "name": "jobs",
        "in": "query",
        "required": false,
        "description": "Array of job IDs to filter or batch-operate on.",
        "style": "form",
        "explode": true,
        "schema": {
          "type": "array",
          "items": {
            "type": "integer"
          }
        }
      }
    },
    "headers": {
      "RateLimitLimit": {
        "description": "Request limit for the current rate-limit window. Returned for unapproved API keys.",
        "schema": {
          "type": "integer"
        }
      },
      "RateLimitRemaining": {
        "description": "Remaining requests in the current rate-limit window. Returned for unapproved API keys.",
        "schema": {
          "type": "integer"
        }
      },
      "RateLimitReset": {
        "description": "Unix timestamp when the current rate-limit window resets. Returned for unapproved API keys.",
        "schema": {
          "type": "integer",
          "format": "int64"
        }
      }
    },
    "responses": {
      "BadRequest": {
        "description": "Bad request",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/Error"
            },
            "example": {
              "error": {
                "name": "Bad Request",
                "message": "Invalid request parameters",
                "code": 0,
                "status": 400
              }
            }
          }
        }
      },
      "Unauthorized": {
        "description": "Unauthorized",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/Error"
            },
            "example": {
              "error": {
                "name": "Unauthorized",
                "message": "Your request was made with invalid credentials.",
                "code": 0,
                "status": 401
              }
            }
          }
        }
      },
      "Forbidden": {
        "description": "Forbidden",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/Error"
            },
            "example": {
              "error": {
                "name": "Forbidden",
                "message": "You are not allowed to perform this action.",
                "code": 0,
                "status": 403
              }
            }
          }
        }
      },
      "NotFound": {
        "description": "Not found",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/Error"
            },
            "example": {
              "error": {
                "name": "Not Found",
                "message": "Candidate not found",
                "code": 0,
                "status": 404
              }
            }
          }
        }
      },
      "ValidationError": {
        "description": "Validation error",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ValidationError"
            }
          }
        }
      },
      "TooManyRequests": {
        "description": "Too many requests",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/Error"
            },
            "example": {
              "error": {
                "name": "Too Many Requests",
                "message": "Rate limit exceeded",
                "code": 0,
                "status": 429
              }
            }
          }
        }
      },
      "UnsupportedMediaType": {
        "description": "Content-Type must be application/json",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/Error"
            },
            "example": {
              "error": {
                "name": "Unsupported Media Type",
                "message": "Content-Type must be application/json",
                "code": 0,
                "status": 415
              }
            }
          }
        }
      },
      "InternalServerError": {
        "description": "Internal server error",
        "headers": {
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/RateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/RateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/RateLimitReset"
          }
        },
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/Error"
            }
          }
        }
      }
    },
    "schemas": {
      "Error": {
        "type": "object",
        "required": [
          "error"
        ],
        "properties": {
          "error": {
            "type": "object",
            "description": "Error details object.",
            "required": [
              "name",
              "message",
              "code",
              "status"
            ],
            "properties": {
              "name": {
                "type": "string",
                "description": "Human-readable error type (e.g. \"Not Found\", \"Bad Request\", \"Forbidden\")",
                "example": "Not Found"
              },
              "message": {
                "type": "string",
                "description": "Detailed error message",
                "example": "Candidate not found"
              },
              "code": {
                "type": "integer",
                "description": "Application error code (0 for generic errors)",
                "example": 0
              },
              "status": {
                "type": "integer",
                "description": "HTTP status code",
                "example": 404
              }
            }
          }
        },
        "example": {
          "error": {
            "name": "Not Found",
            "message": "Candidate not found",
            "code": 0,
            "status": 404
          }
        }
      },
      "ValidationError": {
        "type": "object",
        "required": [
          "error"
        ],
        "properties": {
          "error": {
            "type": "object",
            "description": "Validation error details object.",
            "required": [
              "name",
              "validation_errors"
            ],
            "properties": {
              "name": {
                "type": "string",
                "description": "Always \"Validation Error\" for validation failures",
                "example": "Validation Error"
              },
              "message": {
                "type": "string"
              },
              "code": {
                "type": "integer",
                "example": 0
              },
              "status": {
                "type": "integer",
                "example": 400
              },
              "validation_errors": {
                "type": "object",
                "description": "Field-level validation errors (field name to error message)",
                "additionalProperties": {
                  "type": "string"
                },
                "example": {
                  "email": "Email cannot be blank.",
                  "first_name": "First Name cannot be blank."
                }
              }
            }
          }
        },
        "example": {
          "error": {
            "name": "Validation Error",
            "message": "",
            "code": 0,
            "status": 400,
            "validation_errors": {
              "email": "Email cannot be blank.",
              "first_name": "First Name cannot be blank."
            }
          }
        }
      },
      "SuccessResponse": {
        "type": "object",
        "required": [
          "success"
        ],
        "properties": {
          "success": {
            "type": "boolean",
            "description": "Always true on success."
          }
        }
      },
      "Pagination": {
        "type": "object",
        "required": [
          "page_size",
          "page_count",
          "page",
          "total_count"
        ],
        "properties": {
          "page_size": {
            "type": "integer",
            "description": "Items per page."
          },
          "page_count": {
            "type": "integer",
            "description": "Total number of pages."
          },
          "page": {
            "type": "integer",
            "description": "Current page number."
          },
          "total_count": {
            "type": "integer",
            "description": "Total number of items."
          }
        }
      },
      "IdName": {
        "type": "object",
        "required": [
          "id",
          "name"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier."
          },
          "name": {
            "type": "string",
            "description": "Display name."
          }
        }
      },
      "FileData": {
        "type": "object",
        "required": [
          "data",
          "file_name",
          "mime_type"
        ],
        "properties": {
          "data": {
            "type": "string",
            "description": "Base64 content"
          },
          "file_name": {
            "type": "string",
            "description": "Original file name."
          },
          "mime_type": {
            "type": "string",
            "description": "MIME type (e.g. application/pdf)."
          },
          "size": {
            "type": "integer",
            "description": "Optional for uploads, returned in responses"
          }
        }
      },
      "ProfileAnswer": {
        "type": "object",
        "required": [
          "question_id",
          "question_text",
          "value"
        ],
        "properties": {
          "question_id": {
            "type": "integer",
            "description": "Question ID."
          },
          "question_text": {
            "type": "string",
            "description": "Question label."
          },
          "value": {
            "description": "Answer value (string, array, or null)."
          }
        }
      },
      "CandidateApplicationSummary": {
        "type": "object",
        "required": [
          "id",
          "job"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Application ID."
          },
          "job": {
            "type": "object",
            "description": "Job summary (id, title, status).",
            "required": [
              "id",
              "title"
            ],
            "properties": {
              "id": {
                "type": "integer"
              },
              "title": {
                "type": "string"
              }
            }
          },
          "stage": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ]
          }
        }
      },
      "Candidate": {
        "type": "object",
        "required": [
          "id",
          "company_id",
          "created_at",
          "updated_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "alias": {
            "type": [
              "string",
              "null"
            ],
            "description": "Short alphanumeric alias used in profile URLs. Use this to build candidate profile links — `https://app.100hires.com/candidate/{alias}`. Also accepted as `{id}` in API requests.",
            "example": "dtGeby2"
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL of the candidate in the 100Hires recruiter app. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/candidate/dtGeby2"
          },
          "company_id": {
            "type": "integer",
            "description": "ID of the company this candidate belongs to"
          },
          "first_name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Candidate's first name"
          },
          "last_name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Candidate's last name"
          },
          "emails": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "type": "string",
                  "format": "email"
                }
              },
              {
                "type": "null"
              }
            ],
            "description": "List of candidate email addresses"
          },
          "phones": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "type": "string"
                }
              },
              {
                "type": "null"
              }
            ],
            "description": "List of candidate phone numbers"
          },
          "source": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "How the candidate was sourced (e.g. LinkedIn, Referral)"
          },
          "origin": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Where the candidate originally came from (e.g. job board name)"
          },
          "profile": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ProfileAnswer"
            },
            "description": "Candidate profile field answers (application form responses). Present only when `view=full` (default); omitted entirely when `view=summary` to keep list responses inside the agent context budget — a single candidate can carry dozens of free-form answers."
          },
          "ip": {
            "type": [
              "string",
              "null"
            ],
            "description": "IP address from which the candidate applied"
          },
          "applications": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CandidateApplicationSummary"
            },
            "description": "Summary of all applications this candidate has across jobs"
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "last_message_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds) of the most recent message (email or SMS) sent to or received from this candidate. Null if no messages exist."
          },
          "days_since_last_message": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Number of whole days since the last message. Computed at request time. Null if no messages exist."
          }
        }
      },
      "ApplicationCandidate": {
        "type": "object",
        "required": [
          "id",
          "company_id",
          "profile",
          "created_at",
          "updated_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "company_id": {
            "type": "integer",
            "description": "ID of the company this candidate belongs to"
          },
          "first_name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Candidate's first name"
          },
          "last_name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Candidate's last name"
          },
          "emails": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "type": "string",
                  "format": "email"
                }
              },
              {
                "type": "null"
              }
            ],
            "description": "List of candidate email addresses"
          },
          "phones": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "type": "string"
                }
              },
              {
                "type": "null"
              }
            ],
            "description": "List of candidate phone numbers"
          },
          "source": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "How the candidate was sourced"
          },
          "origin": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Where the candidate originally came from"
          },
          "profile": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ProfileAnswer"
            },
            "description": "Candidate profile field answers"
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "last_message_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds) of the most recent message (email or SMS) sent to or received from this candidate. Null if no messages exist."
          },
          "days_since_last_message": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Number of whole days since the last message. Computed at request time. Null if no messages exist."
          },
          "ip": {
            "type": [
              "string",
              "null"
            ],
            "description": "IP address from which the candidate applied"
          }
        }
      },
      "CandidateListResponse": {
        "type": "object",
        "required": [
          "candidates",
          "pagination"
        ],
        "properties": {
          "candidates": {
            "type": "array",
            "description": "Array of candidates.",
            "items": {
              "$ref": "#/components/schemas/Candidate"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "CandidateWriteRequest": {
        "type": "object",
        "properties": {
          "company_id": {
            "type": "integer",
            "description": "Target company ID. Required only when the API key has access to multiple companies."
          },
          "first_name": {
            "type": "string",
            "description": "Candidate first name."
          },
          "last_name": {
            "type": "string",
            "description": "Candidate last name."
          },
          "email": {
            "type": "string",
            "format": "email",
            "description": "Candidate email address. Used for deduplication."
          },
          "phone": {
            "type": "string",
            "description": "Candidate phone number."
          },
          "profile": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Key-value map of profile field answers. Keys can be either question text (string) or question_id (integer from GET /questions). Library fields (First name, Last name, Email, Phone, etc.) and custom fields both support text-based keys. Example: {\"Years of experience\": \"5\"} or {\"42\": \"5\"}.\n"
          },
          "job_id": {
            "type": "integer",
            "description": "Job ID to create an application for this candidate. If omitted, candidate is created without an application."
          },
          "stage_id": {
            "type": "integer",
            "description": "Pipeline stage ID for the initial application. Requires job_id. If omitted with job_id, defaults to the first stage."
          },
          "cv": {
            "$ref": "#/components/schemas/FileData"
          },
          "city": {
            "type": "string",
            "description": "Candidate city. Used together with state/country to resolve timezone and location display in the profile header."
          },
          "state": {
            "type": "string",
            "description": "Candidate state or region."
          },
          "country": {
            "type": "string",
            "description": "Candidate country name or ISO 3166-1 alpha-2 code (e.g. 'United States' or 'US')."
          },
          "timezone": {
            "type": "string",
            "description": "IANA timezone (e.g. 'America/Los_Angeles'). If omitted, resolved automatically from city/country. If provided alongside city, overrides the auto-resolved timezone."
          }
        },
        "additionalProperties": false
      },
      "TagListResponse": {
        "type": "object",
        "required": [
          "tags",
          "pagination"
        ],
        "properties": {
          "tags": {
            "type": "array",
            "description": "Array of tags.",
            "items": {
              "type": "string"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "TagWriteRequest": {
        "type": "object",
        "required": [
          "tags"
        ],
        "properties": {
          "tags": {
            "type": "array",
            "description": "Array of tag strings to add.",
            "items": {
              "type": "string"
            }
          }
        },
        "additionalProperties": false
      },
      "ApiAttachment": {
        "type": "object",
        "description": "Unified attachment shape returned by apiV2 endpoints (resumes, candidate files, application attachments, message attachments, call recordings, voicemail audio in nurture campaigns).\n\n`url` is an absolute URL served by the API host (`https://api.100hires.com/v2/attachments/{category}/{uuid}/{file_name}`) and serves the raw file bytes with `Authorization: Bearer <API_KEY>`. The response on `url` sets `Content-Disposition: attachment; filename=\"...\"` with the human-readable filename.\n\nUse `uuid` to reference the attachment in other endpoints (e.g. nurture voicemail step).\n",
        "required": [
          "uuid",
          "url",
          "relative_time",
          "file"
        ],
        "properties": {
          "uuid": {
            "type": "string",
            "format": "uuid",
            "description": "Unique attachment identifier. Stable across API calls; use in referencing endpoints."
          },
          "url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Absolute download URL (e.g. `https://api.100hires.com/v2/attachments/application/{uuid}/{file_name}`). Hit with `Authorization: Bearer <API_KEY>`."
          },
          "relative_time": {
            "type": "string",
            "description": "Human-readable time since upload (e.g. `\"2 days ago\"`)."
          },
          "file": {
            "$ref": "#/components/schemas/AttachmentFile"
          }
        }
      },
      "CandidateFile": {
        "description": "Candidate file attachment returned by `/candidates/{id}/files` and `/candidates/{id}/resume`.",
        "allOf": [
          {
            "$ref": "#/components/schemas/ApiAttachment"
          }
        ]
      },
      "CandidateResumeResponse": {
        "description": "Resume file with optional parsed text content (when `?include=text_content` is used, the response includes a `text` field with the parsed plain-text content).",
        "allOf": [
          {
            "$ref": "#/components/schemas/ApiAttachment"
          },
          {
            "type": "object",
            "properties": {
              "text": {
                "type": "string",
                "nullable": true,
                "description": "Parsed plain-text content of the resume. Only included when `?include=text_content` is specified AND `view=full` (the default). Suppressed when `view=summary` even if the include was requested. May be null if the file format is unsupported or parsing fails."
              }
            }
          }
        ]
      },
      "CandidateFilesResponse": {
        "type": "object",
        "required": [
          "files"
        ],
        "properties": {
          "files": {
            "type": "array",
            "description": "Array of candidate files.",
            "items": {
              "$ref": "#/components/schemas/CandidateFile"
            }
          }
        }
      },
      "CandidateFileUploadRequest": {
        "type": "object",
        "required": [
          "file"
        ],
        "properties": {
          "file": {
            "$ref": "#/components/schemas/FileData"
          }
        },
        "additionalProperties": false
      },
      "AccountMessageListResponse": {
        "type": "object",
        "required": [
          "messages",
          "pagination"
        ],
        "properties": {
          "messages": {
            "type": "array",
            "description": "Array of messages for the specified mail account. Each item uses the same format as `GET /messages/{id}`.",
            "items": {
              "$ref": "#/components/schemas/ScheduledEmail"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "CandidateMessageListResponse": {
        "type": "object",
        "required": [
          "messages",
          "pagination"
        ],
        "properties": {
          "messages": {
            "type": "array",
            "description": "Array of messages.",
            "items": {
              "$ref": "#/components/schemas/CandidateMessage"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "CandidateMessage": {
        "oneOf": [
          {
            "$ref": "#/components/schemas/CandidateMailboxMessage"
          },
          {
            "$ref": "#/components/schemas/CandidateTextingMessage"
          },
          {
            "$ref": "#/components/schemas/CandidateVoicemailMessage"
          },
          {
            "$ref": "#/components/schemas/CandidateInitialMailMessage"
          },
          {
            "$ref": "#/components/schemas/CandidateNotificationMessage"
          }
        ],
        "discriminator": {
          "propertyName": "type",
          "mapping": {
            "mailbox": "#/components/schemas/CandidateMailboxMessage",
            "texting": "#/components/schemas/CandidateTextingMessage",
            "voicemail": "#/components/schemas/CandidateVoicemailMessage",
            "candidate_initial_mail_message": "#/components/schemas/CandidateInitialMailMessage",
            "notification": "#/components/schemas/CandidateNotificationMessage"
          }
        }
      },
      "CandidateMailboxMessage": {
        "type": "object",
        "required": [
          "type",
          "is_sent_by_candidate",
          "message"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Message type discriminator.",
            "enum": [
              "mailbox"
            ]
          },
          "is_sent_by_candidate": {
            "type": "boolean",
            "description": "Whether the candidate sent this message."
          },
          "message": {
            "$ref": "#/components/schemas/MailboxMessage"
          }
        },
        "additionalProperties": false
      },
      "CandidateTextingMessage": {
        "type": "object",
        "required": [
          "type",
          "is_sent_by_candidate",
          "message"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Message type discriminator.",
            "enum": [
              "texting"
            ]
          },
          "is_sent_by_candidate": {
            "type": "boolean",
            "description": "Whether the candidate sent this message."
          },
          "message": {
            "$ref": "#/components/schemas/TextingMessage"
          }
        },
        "additionalProperties": false
      },
      "CandidateVoicemailMessage": {
        "type": "object",
        "required": [
          "type",
          "is_sent_by_candidate",
          "message"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Message type discriminator.",
            "enum": [
              "voicemail"
            ]
          },
          "is_sent_by_candidate": {
            "type": "boolean",
            "description": "Whether the candidate sent this message."
          },
          "message": {
            "$ref": "#/components/schemas/VoicemailMessage"
          }
        },
        "additionalProperties": false
      },
      "CandidateInitialMailMessage": {
        "type": "object",
        "required": [
          "type",
          "is_sent_by_candidate",
          "message"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Message type discriminator.",
            "enum": [
              "candidate_initial_mail_message"
            ]
          },
          "is_sent_by_candidate": {
            "type": "boolean",
            "description": "Whether the candidate sent this message."
          },
          "message": {
            "$ref": "#/components/schemas/InitialMailMessage"
          }
        },
        "additionalProperties": false
      },
      "CandidateNotificationMessage": {
        "type": "object",
        "required": [
          "type",
          "is_sent_by_candidate",
          "message"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Message type discriminator.",
            "enum": [
              "notification"
            ]
          },
          "is_sent_by_candidate": {
            "type": "boolean",
            "description": "Whether the candidate sent this message."
          },
          "message": {
            "$ref": "#/components/schemas/NotificationMessage"
          }
        },
        "additionalProperties": false
      },
      "MailboxMessage": {
        "type": "object",
        "required": [
          "id",
          "from",
          "to",
          "cc",
          "subject",
          "date",
          "schedule",
          "opensCount",
          "opens",
          "autoJobId",
          "isNurtured"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Message ID."
          },
          "from": {
            "type": "string",
            "nullable": true,
            "description": "Sender address."
          },
          "to": {
            "type": "string",
            "description": "Recipient address."
          },
          "cc": {
            "type": "string",
            "description": "CC recipients."
          },
          "subject": {
            "type": "string",
            "description": "Message subject."
          },
          "body": {
            "type": "string",
            "description": "Message body content. Present only when `view=full` (default); omitted entirely when `view=summary` — message bodies can run into tens of KB."
          },
          "date": {
            "type": "string",
            "description": "Message date."
          },
          "attachments": {
            "type": "array",
            "description": "Message attachments. Present only when `view=full` (default); omitted entirely when `view=summary`.",
            "items": {
              "$ref": "#/components/schemas/Attachment"
            }
          },
          "schedule": {
            "oneOf": [
              {
                "type": "string",
                "enum": [
                  ""
                ]
              },
              {
                "$ref": "#/components/schemas/MailboxSchedule"
              }
            ]
          },
          "opensCount": {
            "type": "integer",
            "description": "Number of times opened."
          },
          "opens": {
            "type": "array",
            "description": "Array of open tracking events.",
            "items": {
              "$ref": "#/components/schemas/MailboxOpenEvent"
            }
          },
          "autoJobId": {
            "oneOf": [
              {
                "type": "integer"
              },
              {
                "type": "string"
              }
            ]
          },
          "isNurtured": {
            "type": "boolean",
            "description": "Whether sent via nurture campaign."
          }
        },
        "additionalProperties": false
      },
      "MailboxSchedule": {
        "type": "object",
        "required": [
          "senderId",
          "isForceSend",
          "isFailed",
          "scheduleSendError",
          "isScheduled",
          "scheduledDay",
          "sendAt",
          "humanDatetime",
          "systemDatetime"
        ],
        "properties": {
          "senderId": {
            "type": "integer",
            "nullable": true,
            "description": "Sender mail account ID."
          },
          "isForceSend": {
            "type": "boolean",
            "description": "Whether forced to send immediately."
          },
          "isFailed": {
            "type": "boolean",
            "description": "Whether send failed."
          },
          "scheduleSendError": {
            "type": "string",
            "nullable": true,
            "description": "Error message on failure."
          },
          "isScheduled": {
            "type": "boolean",
            "description": "Whether currently scheduled."
          },
          "scheduledDay": {
            "type": "string",
            "description": "Scheduled date."
          },
          "sendAt": {
            "type": "integer",
            "format": "int64",
            "description": "Scheduled send time."
          },
          "humanDatetime": {
            "type": "string",
            "description": "Human-readable scheduled time."
          },
          "systemDatetime": {
            "type": "string",
            "description": "System scheduled time."
          }
        },
        "additionalProperties": false
      },
      "MailboxOpenEvent": {
        "type": "object",
        "required": [
          "label"
        ],
        "properties": {
          "label": {
            "type": "string",
            "description": "Open event label."
          }
        },
        "additionalProperties": false
      },
      "TextingMessage": {
        "type": "object",
        "required": [
          "id",
          "body",
          "date",
          "isFailed",
          "sendError",
          "schedule",
          "autoJobId",
          "isNurtured",
          "to"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Message ID."
          },
          "body": {
            "type": "string",
            "description": "Message body content."
          },
          "date": {
            "type": "string",
            "description": "Message date."
          },
          "isFailed": {
            "type": "boolean",
            "description": "Whether delivery failed."
          },
          "sendError": {
            "type": "string",
            "nullable": true,
            "description": "Error message on failure."
          },
          "schedule": {
            "oneOf": [
              {
                "type": "string",
                "enum": [
                  ""
                ]
              },
              {
                "$ref": "#/components/schemas/TextingSchedule"
              }
            ]
          },
          "autoJobId": {
            "oneOf": [
              {
                "type": "integer"
              },
              {
                "type": "string"
              }
            ]
          },
          "isNurtured": {
            "type": "boolean",
            "description": "Whether sent via nurture campaign."
          },
          "to": {
            "type": "string",
            "description": "Recipient address."
          },
          "from": {
            "type": "string",
            "nullable": true,
            "description": "Sender address."
          }
        },
        "additionalProperties": false
      },
      "TextingSchedule": {
        "type": "object",
        "required": [
          "isScheduled",
          "scheduledDay",
          "sendAt",
          "humanDatetime",
          "systemDatetime"
        ],
        "properties": {
          "isScheduled": {
            "type": "boolean",
            "description": "Whether currently scheduled."
          },
          "scheduledDay": {
            "type": "string",
            "description": "Scheduled date."
          },
          "sendAt": {
            "type": "integer",
            "format": "int64",
            "description": "Scheduled send time."
          },
          "humanDatetime": {
            "type": "string",
            "description": "Human-readable scheduled time."
          },
          "systemDatetime": {
            "type": "string",
            "description": "System scheduled time."
          }
        },
        "additionalProperties": false
      },
      "VoicemailMessage": {
        "type": "object",
        "required": [
          "id",
          "date",
          "to",
          "from",
          "attachment",
          "isFailed",
          "sendError",
          "schedule",
          "isCallTook",
          "autoJobId",
          "isNurtured"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Message ID."
          },
          "date": {
            "type": "string",
            "description": "Message date."
          },
          "to": {
            "type": "string",
            "description": "Recipient address."
          },
          "from": {
            "type": "string",
            "nullable": true,
            "description": "Sender address."
          },
          "attachment": {
            "$ref": "#/components/schemas/Attachment"
          },
          "isFailed": {
            "type": "boolean",
            "description": "Whether delivery failed."
          },
          "sendError": {
            "type": "string",
            "nullable": true,
            "description": "Error message on failure."
          },
          "schedule": {
            "oneOf": [
              {
                "type": "string",
                "enum": [
                  ""
                ]
              },
              {
                "$ref": "#/components/schemas/VoicemailSchedule"
              }
            ]
          },
          "isCallTook": {
            "type": "boolean",
            "description": "Whether the call was answered."
          },
          "autoJobId": {
            "oneOf": [
              {
                "type": "integer"
              },
              {
                "type": "string"
              }
            ]
          },
          "isNurtured": {
            "type": "boolean",
            "description": "Whether sent via nurture campaign."
          }
        },
        "additionalProperties": false
      },
      "VoicemailSchedule": {
        "type": "object",
        "required": [
          "isScheduled",
          "humanDatetime",
          "systemDatetime"
        ],
        "properties": {
          "isScheduled": {
            "type": "boolean",
            "description": "Whether currently scheduled."
          },
          "humanDatetime": {
            "type": "string",
            "description": "Human-readable scheduled time."
          },
          "systemDatetime": {
            "type": "string",
            "description": "System scheduled time."
          }
        },
        "additionalProperties": false
      },
      "InitialMailMessage": {
        "type": "object",
        "required": [
          "id",
          "from",
          "to",
          "subject",
          "body",
          "date"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Message ID."
          },
          "from": {
            "type": "string",
            "description": "Sender address."
          },
          "to": {
            "type": "string",
            "description": "Recipient address."
          },
          "subject": {
            "type": "string",
            "description": "Message subject."
          },
          "body": {
            "type": "string",
            "description": "Message body content."
          },
          "date": {
            "type": "string",
            "description": "Message date."
          }
        },
        "additionalProperties": false
      },
      "NotificationMessage": {
        "type": "object",
        "required": [
          "id",
          "from",
          "to",
          "subject",
          "body",
          "date",
          "schedule"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Message ID."
          },
          "from": {
            "type": "string",
            "description": "Sender address."
          },
          "to": {
            "type": "string",
            "description": "Recipient address."
          },
          "subject": {
            "type": "string",
            "description": "Message subject."
          },
          "body": {
            "type": "string",
            "description": "Message body content."
          },
          "date": {
            "type": "string",
            "description": "Message date."
          },
          "schedule": {
            "oneOf": [
              {
                "type": "string",
                "enum": [
                  ""
                ]
              },
              {
                "$ref": "#/components/schemas/NotificationMessageSchedule"
              }
            ]
          }
        },
        "additionalProperties": false
      },
      "NotificationMessageSchedule": {
        "type": "object",
        "required": [
          "id",
          "isScheduled",
          "isFailed",
          "humanDatetime",
          "isNotificationMessage"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Schedule ID."
          },
          "isScheduled": {
            "type": "boolean",
            "description": "Whether currently scheduled."
          },
          "isFailed": {
            "type": "boolean",
            "description": "Whether send failed."
          },
          "humanDatetime": {
            "type": "string",
            "description": "Human-readable scheduled time."
          },
          "isNotificationMessage": {
            "type": "boolean",
            "description": "Always true for notification messages."
          }
        },
        "additionalProperties": false
      },
      "NotificationMessageUpdateRequest": {
        "type": "object",
        "required": [
          "subject",
          "body"
        ],
        "properties": {
          "subject": {
            "type": "string",
            "maxLength": 500,
            "description": "Email subject line."
          },
          "body": {
            "type": "string",
            "description": "Email body as HTML."
          },
          "scheduled_at": {
            "type": "integer",
            "format": "int64",
            "nullable": true,
            "description": "Unix timestamp (seconds) to reschedule send time. If omitted, the existing schedule is preserved."
          }
        },
        "additionalProperties": false
      },
      "Attachment": {
        "description": "Message attachment (deprecated name, alias for `ApiAttachment`).",
        "allOf": [
          {
            "$ref": "#/components/schemas/ApiAttachment"
          }
        ]
      },
      "AttachmentFile": {
        "type": "object",
        "required": [
          "is_image",
          "orig_file_name",
          "file_ext",
          "file_type",
          "readable_size"
        ],
        "properties": {
          "is_image": {
            "type": "boolean",
            "nullable": true,
            "description": "Whether the file is an image."
          },
          "orig_file_name": {
            "type": "string",
            "description": "Original file name."
          },
          "file_ext": {
            "type": "string",
            "description": "File extension."
          },
          "file_type": {
            "type": "string",
            "description": "File type category."
          },
          "readable_size": {
            "type": "string",
            "description": "Human-readable file size."
          }
        },
        "additionalProperties": false
      },
      "ScheduledEmail": {
        "type": "object",
        "required": [
          "type",
          "message"
        ],
        "properties": {
          "type": {
            "type": "string",
            "enum": [
              "mailbox"
            ],
            "description": "Message channel type for scheduler-backed message endpoints."
          },
          "message": {
            "$ref": "#/components/schemas/MailboxMessage",
            "description": "Mailbox message payload, including envelope, body, attachments, and schedule metadata."
          }
        },
        "additionalProperties": false
      },
      "ScheduledEmailCreateRequest": {
        "type": "object",
        "required": [
          "to",
          "subject",
          "body"
        ],
        "properties": {
          "from_account_id": {
            "type": "integer",
            "nullable": true,
            "description": "Optional sending mail account ID. Use `GET /users/{user_id}/mail-accounts` to list available accounts for a user, or `GET /companies/mail-accounts` to list all accounts. If omitted, the API key owner's default mail account is used."
          },
          "to": {
            "type": "array",
            "description": "Primary recipient email addresses.",
            "items": {
              "type": "string",
              "format": "email"
            }
          },
          "cc": {
            "type": "array",
            "description": "Carbon-copy recipient email addresses.",
            "items": {
              "type": "string",
              "format": "email"
            }
          },
          "bcc": {
            "type": "array",
            "description": "Blind carbon-copy recipient email addresses.",
            "items": {
              "type": "string",
              "format": "email"
            }
          },
          "subject": {
            "type": "string",
            "description": "Email subject line."
          },
          "body": {
            "type": "string",
            "description": "Email body as HTML."
          },
          "scheduled_at": {
            "type": "integer",
            "format": "int64",
            "nullable": true,
            "description": "Unix timestamp (seconds). If omitted, defaults to created time plus 900 seconds."
          },
          "application_id": {
            "type": "integer",
            "nullable": true,
            "description": "Optional application ID linked to this message."
          },
          "reply_to_email_id": {
            "type": "integer",
            "nullable": true,
            "description": "Optional mailbox message ID to reply to."
          },
          "send_in_new_thread": {
            "type": "boolean",
            "default": false,
            "description": "Whether to send the message as a new thread instead of replying in an existing thread."
          }
        },
        "additionalProperties": false
      },
      "ScheduledEmailUpdateRequest": {
        "type": "object",
        "required": [
          "to",
          "subject",
          "body"
        ],
        "properties": {
          "from_account_id": {
            "type": "integer",
            "nullable": true,
            "description": "Optional sending mail account ID. Use `GET /users/{user_id}/mail-accounts` to list available accounts for a user, or `GET /companies/mail-accounts` to list all accounts. If omitted, the API key owner's default mail account is used."
          },
          "to": {
            "type": "array",
            "description": "Primary recipient email addresses.",
            "items": {
              "type": "string",
              "format": "email"
            }
          },
          "cc": {
            "type": "array",
            "description": "Carbon-copy recipient email addresses.",
            "items": {
              "type": "string",
              "format": "email"
            }
          },
          "bcc": {
            "type": "array",
            "description": "Blind carbon-copy recipient email addresses.",
            "items": {
              "type": "string",
              "format": "email"
            }
          },
          "subject": {
            "type": "string",
            "description": "Updated email subject line."
          },
          "body": {
            "type": "string",
            "description": "Updated email body as HTML."
          },
          "scheduled_at": {
            "type": "integer",
            "format": "int64",
            "nullable": true,
            "description": "Updated send time as a Unix timestamp in seconds."
          },
          "reply_to_email_id": {
            "type": "integer",
            "nullable": true,
            "description": "Optional mailbox message ID to reply to."
          },
          "send_in_new_thread": {
            "type": "boolean",
            "description": "Whether to send the updated message as a new thread."
          }
        },
        "additionalProperties": false
      },
      "Activity": {
        "type": "object",
        "required": [
          "event_id",
          "candidate_id",
          "application_id",
          "user_id",
          "event",
          "created_at"
        ],
        "properties": {
          "event_id": {
            "type": "integer",
            "description": "Unique ID of the timeline event"
          },
          "candidate_id": {
            "type": "integer",
            "description": "ID of the candidate this event belongs to"
          },
          "application_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "ID of the job application this event is linked to, if any"
          },
          "user_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "ID of the user who triggered this event, if applicable"
          },
          "event": {
            "$ref": "#/components/schemas/ActivityEvent"
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          }
        }
      },
      "ActivityEvent": {
        "description": "Event payload. The shape depends on the event `type`. Text-bubble events (assign_job, candidate_rate, assign_sources, assign_tags, qualification, profile_mutation, validate_emails, stage_moved, enrichment, automation_action_triggered) all share the same structure. Special events (call, comment, copilot_response) have their own shape. When event data is unavailable (e.g. referenced record was deleted), `type` is `missed`.\n",
        "oneOf": [
          {
            "$ref": "#/components/schemas/ActivityEventTextBubble"
          },
          {
            "$ref": "#/components/schemas/ActivityEventCall"
          },
          {
            "$ref": "#/components/schemas/ActivityEventComment"
          },
          {
            "$ref": "#/components/schemas/ActivityEventCopilotResponse"
          },
          {
            "$ref": "#/components/schemas/ActivityEventMissed"
          }
        ]
      },
      "ActivityEventTextBubble": {
        "type": "object",
        "description": "Shared structure for all text-bubble events: assign_job, candidate_rate, assign_sources, assign_tags, qualification, profile_mutation, validate_emails, stage_moved, enrichment, automation_action_triggered.\n",
        "required": [
          "type",
          "is_text_bubble",
          "data"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Event type identifier.",
            "enum": [
              "assign_job",
              "candidate_rate",
              "assign_sources",
              "assign_tags",
              "qualification",
              "profile_mutation",
              "validate_emails",
              "stage_moved",
              "enrichment",
              "automation_action_triggered"
            ]
          },
          "is_text_bubble": {
            "type": "boolean",
            "description": "Always true for text bubble events.",
            "enum": [
              true
            ]
          },
          "data": {
            "type": "object",
            "description": "Event data payload.",
            "required": [
              "text",
              "date",
              "relative_time",
              "full_time"
            ],
            "properties": {
              "text": {
                "type": "string",
                "description": "HTML-formatted description of the event"
              },
              "date": {
                "type": "string",
                "description": "Short formatted date (e.g. \"Jan 1\")"
              },
              "relative_time": {
                "type": "string",
                "description": "Human-readable relative time (e.g. \"2 days ago\")"
              },
              "full_time": {
                "type": "string",
                "description": "Full formatted datetime string"
              },
              "from_stage_id": {
                "type": "integer",
                "nullable": true,
                "description": "Pipeline stage ID the candidate was in before qualification/disqualification. Only present for `qualification` events."
              },
              "from_stage_name": {
                "type": "string",
                "nullable": true,
                "description": "Pipeline stage name the candidate was in before qualification/disqualification. Only present for `qualification` events."
              }
            }
          }
        }
      },
      "ActivityEventCall": {
        "type": "object",
        "description": "Voice call event",
        "required": [
          "type",
          "call"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Event type identifier.",
            "enum": [
              "call"
            ]
          },
          "call": {
            "type": "object",
            "description": "Call details.",
            "required": [
              "from",
              "to",
              "status",
              "datetime",
              "relative_datetime",
              "duration"
            ],
            "properties": {
              "from": {
                "type": "object",
                "description": "Caller who initiated the call",
                "required": [
                  "label",
                  "photo"
                ],
                "properties": {
                  "label": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "description": "Display name or formatted phone number"
                  },
                  "photo": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "description": "URL of the caller's photo"
                  }
                }
              },
              "to": {
                "type": "object",
                "description": "Caller who received the call",
                "required": [
                  "label",
                  "photo"
                ],
                "properties": {
                  "label": {
                    "type": [
                      "string",
                      "null"
                    ]
                  },
                  "photo": {
                    "type": [
                      "string",
                      "null"
                    ]
                  }
                }
              },
              "status": {
                "type": "string",
                "description": "Human-readable call status (e.g. \"Completed\", \"No answer\")"
              },
              "datetime": {
                "type": "string",
                "description": "Full formatted datetime of the call"
              },
              "relative_datetime": {
                "type": "string",
                "description": "Relative time string"
              },
              "duration": {
                "type": "string",
                "description": "Formatted call duration (e.g. \"2 minutes\")"
              },
              "attachment": {
                "description": "Call recording attachment, if available.",
                "allOf": [
                  {
                    "$ref": "#/components/schemas/ApiAttachment"
                  }
                ]
              },
              "transcription": {
                "type": [
                  "object",
                  "null"
                ],
                "description": "Transcription details. Null when no transcription is available for this call.",
                "properties": {
                  "status": {
                    "type": "string",
                    "description": "Transcription status (e.g. \"completed\", \"pending\", \"failed\")."
                  },
                  "text": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "description": "Full transcribed call text. Present only when `view=full` (default); replaced with `text_preview` when `view=summary`. Long calls can produce 5-50 KB of transcript and dominate the response budget."
                  },
                  "text_preview": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "description": "First 200 UTF-8 characters of the transcription text with `...` suffix when truncated. Present only when `view=summary`."
                  },
                  "language": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "description": "Detected/configured language code."
                  },
                  "is_billing_error": {
                    "type": "boolean",
                    "description": "True when transcription failed due to insufficient AI credits."
                  }
                }
              }
            }
          }
        }
      },
      "ActivityEventComment": {
        "type": "object",
        "description": "Candidate comment event",
        "required": [
          "type",
          "comment"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Event type identifier.",
            "enum": [
              "comment"
            ]
          },
          "comment": {
            "type": "object",
            "description": "Comment details.",
            "required": [
              "id",
              "candidate_id",
              "user_id",
              "author",
              "photo",
              "date",
              "datetime",
              "relative_time",
              "visible",
              "is_edit",
              "attachments"
            ],
            "properties": {
              "id": {
                "type": "integer"
              },
              "candidate_id": {
                "type": "integer"
              },
              "user_id": {
                "type": "integer"
              },
              "author": {
                "type": "string",
                "description": "Full name of the comment author"
              },
              "photo": {
                "type": "string",
                "description": "URL of the author's profile photo"
              },
              "text": {
                "type": "string",
                "description": "Comment text (may contain HTML). Present only when `view=full` (default); replaced with `text_preview` when `view=summary`."
              },
              "text_preview": {
                "type": "string",
                "description": "First 200 UTF-8 characters of the comment text with `...` suffix when truncated. Present only when `view=summary`."
              },
              "date": {
                "type": "string",
                "description": "Short formatted date"
              },
              "datetime": {
                "type": "string",
                "description": "Full formatted datetime"
              },
              "relative_time": {
                "type": "string"
              },
              "visible": {
                "type": "string",
                "description": "Visibility scope of the comment",
                "enum": [
                  "all",
                  "owner",
                  "private"
                ]
              },
              "is_edit": {
                "type": "boolean",
                "description": "Whether the comment is currently being edited"
              },
              "attachments": {
                "type": "array",
                "items": {
                  "$ref": "#/components/schemas/ApiAttachment"
                }
              }
            }
          }
        }
      },
      "ActivityEventCopilotResponse": {
        "type": "object",
        "description": "AI Copilot response event",
        "required": [
          "type",
          "copilot_response"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Event type identifier.",
            "enum": [
              "copilot_response"
            ]
          },
          "copilot_response": {
            "type": "object",
            "description": "AI copilot response details.",
            "required": [
              "id",
              "status",
              "error",
              "can_retry",
              "is_billing_error",
              "relative_time",
              "datetime",
              "user"
            ],
            "properties": {
              "id": {
                "type": "integer"
              },
              "user_prompt": {
                "type": "string",
                "description": "The question the user asked the AI. Present only when `view=full` (default); replaced with `user_prompt_preview` when `view=summary`."
              },
              "user_prompt_preview": {
                "type": [
                  "string",
                  "null"
                ],
                "description": "First 200 UTF-8 characters of `user_prompt` with `...` suffix when truncated. Present only when `view=summary`."
              },
              "response": {
                "type": [
                  "string",
                  "null"
                ],
                "description": "The AI-generated answer, null if not yet completed. Present only when `view=full` (default); replaced with `response_preview` when `view=summary`."
              },
              "response_preview": {
                "type": [
                  "string",
                  "null"
                ],
                "description": "First 200 UTF-8 characters of `response` with `...` suffix when truncated. Present only when `view=summary` — LLM answers can run into tens of KB and blow the agent context budget."
              },
              "status": {
                "type": "string",
                "enum": [
                  "pending",
                  "processing",
                  "completed",
                  "failed"
                ]
              },
              "error": {
                "type": [
                  "string",
                  "null"
                ],
                "description": "Error message if status is failed"
              },
              "can_retry": {
                "type": "boolean",
                "description": "Whether this response can be retried"
              },
              "is_billing_error": {
                "type": "boolean",
                "description": "Whether the failure was due to insufficient AI credits"
              },
              "relative_time": {
                "type": "string"
              },
              "datetime": {
                "type": "string",
                "description": "Formatted datetime (Y-m-d H:i:s)"
              },
              "user": {
                "type": [
                  "object",
                  "null"
                ],
                "description": "User who requested the AI response",
                "properties": {
                  "id": {
                    "type": "integer"
                  },
                  "name": {
                    "type": "string"
                  },
                  "photo": {
                    "type": "string"
                  }
                }
              }
            }
          }
        }
      },
      "ActivityEventMissed": {
        "type": "object",
        "description": "Returned when event data is unavailable (e.g. referenced record was deleted)",
        "required": [
          "type"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Event type identifier.",
            "enum": [
              "missed"
            ]
          }
        }
      },
      "ActivityListResponse": {
        "type": "object",
        "required": [
          "activities",
          "pagination",
          "page_size"
        ],
        "properties": {
          "activities": {
            "type": "array",
            "description": "Array of activity events.",
            "items": {
              "$ref": "#/components/schemas/Activity"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          },
          "page_size": {
            "type": "integer",
            "description": "Items per page. Duplicated at top level for backward compatibility (also available in `pagination.page_size`)."
          }
        }
      },
      "CandidateDisqualifyRequest": {
        "type": "object",
        "properties": {
          "reasons": {
            "type": "array",
            "description": "Array of rejection reason IDs from GET /taxonomy/rejection-reasons.",
            "items": {
              "oneOf": [
                {
                  "type": "integer"
                },
                {
                  "type": "string"
                }
              ]
            }
          }
        },
        "additionalProperties": false
      },
      "CandidateDisqualifyResponse": {
        "type": "object",
        "required": [
          "success",
          "rejected_applications"
        ],
        "properties": {
          "success": {
            "type": "boolean",
            "description": "Whether disqualification succeeded."
          },
          "rejected_applications": {
            "type": "array",
            "description": "Array of rejected application IDs.",
            "items": {
              "type": "integer"
            }
          }
        }
      },
      "Application": {
        "type": "object",
        "required": [
          "id",
          "candidate_id",
          "job_id",
          "company_id",
          "status",
          "is_disqualified",
          "created_at",
          "updated_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "candidate_id": {
            "type": "integer",
            "description": "ID of the candidate"
          },
          "job_id": {
            "type": "integer",
            "description": "ID of the job"
          },
          "job_alias": {
            "type": [
              "string",
              "null"
            ],
            "description": "Short alias of the job, usable in URLs (e.g. 79SZHfT)",
            "example": "79SZHfT"
          },
          "internal_job_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Company's internal job identifier"
          },
          "company_id": {
            "type": "integer",
            "description": "ID of the company"
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL of the application's view (candidate page in this job) in the 100Hires recruiter app. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/candidate/dtGeby2/79SZHfT"
          },
          "stage": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Current pipeline stage of the application"
          },
          "status": {
            "type": "string",
            "enum": [
              "active",
              "hired",
              "rejected"
            ],
            "description": "Application status. Changes via hire/reject/unreject actions."
          },
          "is_disqualified": {
            "type": "boolean",
            "description": "Whether the candidate is disqualified for this application"
          },
          "cv": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/ApplicationCvData"
              },
              {
                "type": "null"
              }
            ],
            "description": "Resume/CV data attached to this application"
          },
          "rejected_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "rejection_reason": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "$ref": "#/components/schemas/IdName"
                }
              },
              {
                "type": "null"
              }
            ],
            "description": "Reasons for rejection. Null if not rejected."
          },
          "hired_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "hiring_team": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "$ref": "#/components/schemas/JobHiringTeamMember"
                }
              },
              {
                "type": "null"
              }
            ],
            "description": "Team members assigned to this application's job"
          },
          "custom_fields": {
            "oneOf": [
              {
                "type": "object",
                "additionalProperties": true
              },
              {
                "type": "null"
              }
            ],
            "description": "Custom field values as key-value pairs"
          },
          "ai_score": {
            "type": [
              "integer",
              "null"
            ],
            "description": "AI-generated candidate fit score (0-100)"
          },
          "ai_recommendation": {
            "type": [
              "string",
              "null"
            ],
            "description": "AI-generated recommendation label (e.g. Strong, Good, Weak)"
          },
          "ai_scoring_updated_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds) of the latest completed AI scoring result"
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "last_message_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds) of the most recent message (email or SMS) sent to or received from the candidate in this application's company. Null if no messages exist."
          },
          "days_since_last_message": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Number of whole days since the last message. Computed at request time. Null if no messages exist."
          },
          "candidate": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/ApplicationCandidate"
              },
              {
                "type": "null"
              }
            ],
            "description": "Embedded candidate data (included when requested via `include=candidate`)"
          },
          "job": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/Job"
              },
              {
                "type": "null"
              }
            ],
            "description": "Embedded job payload (included when requested via `include=job`). Use `job.url_backoffice` to deep-link UI widgets to the job's pipeline view in the recruiter app."
          }
        }
      },
      "ApplicationAiScoreCriterion": {
        "type": "object",
        "required": [
          "criterion_text",
          "score",
          "justification"
        ],
        "properties": {
          "criterion_title": {
            "type": [
              "string",
              "null"
            ],
            "description": "Short criterion title."
          },
          "criterion_text": {
            "type": "string",
            "description": "Full criterion description."
          },
          "score": {
            "type": "integer",
            "description": "Score for this criterion (0-100)."
          },
          "justification": {
            "type": [
              "string",
              "null"
            ],
            "description": "AI explanation for the score."
          },
          "followup_questions": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "type": "string"
                }
              },
              {
                "type": "null"
              }
            ]
          }
        }
      },
      "ApplicationAiScorePayload": {
        "type": "object",
        "required": [
          "uuid",
          "job_id",
          "job_title",
          "job_url",
          "summary",
          "total_score",
          "criteria",
          "rate",
          "date"
        ],
        "properties": {
          "uuid": {
            "type": [
              "string",
              "null"
            ],
            "description": "Unique scoring session ID."
          },
          "job_id": {
            "type": "integer",
            "description": "Job ID."
          },
          "job_title": {
            "type": [
              "string",
              "null"
            ],
            "description": "Job title."
          },
          "job_url": {
            "type": [
              "string",
              "null"
            ],
            "description": "Job URL."
          },
          "summary": {
            "type": [
              "string",
              "null"
            ],
            "description": "AI-generated summary."
          },
          "total_score": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Total score (0-100)."
          },
          "criteria": {
            "type": "array",
            "description": "Array of scoring criteria with scores.",
            "items": {
              "$ref": "#/components/schemas/ApplicationAiScoreCriterion"
            }
          },
          "rate": {
            "type": "integer",
            "description": "Overall recommendation (e.g. strong_yes, yes, no)."
          },
          "date": {
            "type": [
              "string",
              "null"
            ],
            "description": "Scoring date."
          }
        }
      },
      "ApplicationAiScoreResponse": {
        "type": "object",
        "required": [
          "score"
        ],
        "properties": {
          "score": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/ApplicationAiScorePayload"
              },
              {
                "type": "null"
              }
            ]
          }
        }
      },
      "ApplicationStageHistoryEntry": {
        "type": "object",
        "required": [
          "from_stage_id",
          "from_stage_name",
          "to_stage_id",
          "to_stage_name",
          "moved_at",
          "moved_by_type",
          "moved_by_user_id",
          "source"
        ],
        "properties": {
          "from_stage_id": {
            "type": "integer",
            "nullable": true,
            "description": "Previous stage id. `null` for the initial assignment."
          },
          "from_stage_name": {
            "type": "string",
            "nullable": true,
            "description": "Previous stage name. `null` for the initial assignment."
          },
          "to_stage_id": {
            "type": "integer",
            "description": "Stage id the application was moved to."
          },
          "to_stage_name": {
            "type": "string",
            "nullable": true,
            "description": "Stage name the application was moved to. `null` if the stage has been hard-deleted."
          },
          "moved_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds) of the transition."
          },
          "moved_by_type": {
            "type": "string",
            "enum": [
              "user",
              "automation",
              "system"
            ],
            "description": "Who/what initiated the move. `user` = manual move, `automation` = automation rule/form watcher, `system` = initial assignment or unattributed."
          },
          "moved_by_user_id": {
            "type": "integer",
            "nullable": true,
            "description": "ID of the user that performed the move. Populated only when `moved_by_type = user`."
          },
          "source": {
            "type": "string",
            "nullable": true,
            "description": "What caused the transition. Format: `<assign_type>` or `<assign_type>:<board_name>`. Examples: `apply:indeed`, `form_watcher`, `user`, `api_v2`. `null` for historical records created before source tracking was added."
          }
        }
      },
      "ApplicationStageHistoryResponse": {
        "type": "object",
        "required": [
          "history"
        ],
        "properties": {
          "history": {
            "type": "array",
            "description": "Chronological list of stage transitions (oldest first), including the initial assignment.",
            "items": {
              "$ref": "#/components/schemas/ApplicationStageHistoryEntry"
            }
          }
        }
      },
      "ApplicationListResponse": {
        "type": "object",
        "required": [
          "applications",
          "pagination"
        ],
        "properties": {
          "applications": {
            "type": "array",
            "description": "Array of applications.",
            "items": {
              "$ref": "#/components/schemas/Application"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "Interview": {
        "type": "object",
        "required": [
          "id",
          "application_id",
          "job_id",
          "candidate_id",
          "start_time",
          "end_time",
          "status",
          "interviewers",
          "created_at",
          "updated_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "application_id": {
            "type": "integer",
            "description": "ID of the related application"
          },
          "job_id": {
            "type": "integer",
            "description": "ID of the related job"
          },
          "candidate_id": {
            "type": "integer",
            "description": "ID of the related candidate"
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL of the candidate's interviews tab in the 100Hires recruiter app where this interview appears. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/candidate/dtGeby2#/profile/interviews"
          },
          "candidate": {
            "$ref": "#/components/schemas/Candidate",
            "description": "Embedded candidate data (included when requested)"
          },
          "application": {
            "$ref": "#/components/schemas/Application",
            "description": "Embedded application data (included when requested)"
          },
          "job": {
            "$ref": "#/components/schemas/Job",
            "description": "Embedded job data (included when requested)"
          },
          "start_time": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "end_time": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "status": {
            "type": "string",
            "enum": [
              "scheduled",
              "completed"
            ],
            "description": "Interview status"
          },
          "interviewers": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "user_id": {
                  "type": "integer"
                },
                "name": {
                  "type": "string"
                },
                "email": {
                  "type": "string"
                }
              }
            },
            "description": "List of interviewers participating in this interview"
          },
          "location": {
            "type": [
              "string",
              "null"
            ],
            "description": "Physical location of the interview"
          },
          "meeting_url": {
            "type": [
              "string",
              "null"
            ],
            "description": "Video conferencing or meeting URL"
          },
          "stage": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Pipeline stage at the time the interview was scheduled"
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          }
        }
      },
      "InterviewListResponse": {
        "type": "object",
        "required": [
          "interviews",
          "pagination"
        ],
        "properties": {
          "interviews": {
            "type": "array",
            "description": "Array of interviews.",
            "items": {
              "$ref": "#/components/schemas/Interview"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "InterviewCreateRequest": {
        "type": "object",
        "required": [
          "start_time",
          "end_time",
          "interviewer_ids"
        ],
        "properties": {
          "start_time": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "end_time": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds, must be greater than start_time)"
          },
          "interviewer_ids": {
            "type": "array",
            "items": {
              "type": "integer"
            },
            "description": "List of user IDs who will conduct the interview"
          },
          "location": {
            "type": "string",
            "maxLength": 255,
            "description": "Location string; resolved to existing record or created automatically"
          }
        }
      },
      "ApplicationCreateRequest": {
        "type": "object",
        "required": [
          "candidate_id",
          "job_id"
        ],
        "properties": {
          "candidate_id": {
            "type": "string",
            "pattern": "^[A-Za-z0-9_-]+$",
            "description": "Candidate ID (numeric) or alias"
          },
          "job_id": {
            "type": "integer",
            "description": "Job ID to apply the candidate to."
          },
          "stage_id": {
            "type": "integer",
            "description": "Pipeline stage ID. If omitted, defaults to the first stage."
          },
          "cv": {
            "$ref": "#/components/schemas/FileData"
          }
        },
        "additionalProperties": false
      },
      "ApplicationUpdateRequest": {
        "type": "object",
        "properties": {
          "stage_id": {
            "type": "integer",
            "description": "Move application to this pipeline stage."
          },
          "is_disqualified": {
            "type": "boolean",
            "description": "Set to true to disqualify the candidate on this application."
          },
          "cv": {
            "$ref": "#/components/schemas/FileData"
          }
        },
        "additionalProperties": false
      },
      "ApplicationMoveRequest": {
        "type": "object",
        "required": [
          "stage_id"
        ],
        "properties": {
          "stage_id": {
            "type": "integer",
            "description": "Target pipeline stage ID."
          }
        },
        "additionalProperties": false
      },
      "ApplicationRejectRequest": {
        "type": "object",
        "properties": {
          "rejection_reason_id": {
            "type": "integer",
            "description": "Rejection reason ID from GET /taxonomy/rejection-reasons."
          },
          "suppress_notification": {
            "type": "boolean",
            "description": "Set to true to skip sending the rejection email to the candidate."
          }
        },
        "additionalProperties": false
      },
      "ApplicationTransferRequest": {
        "type": "object",
        "required": [
          "job_id"
        ],
        "properties": {
          "job_id": {
            "type": "integer",
            "description": "Target job ID to transfer the application to."
          },
          "stage_id": {
            "type": "integer",
            "description": "Pipeline stage ID on the target job. If omitted, defaults to the first stage."
          }
        },
        "additionalProperties": false
      },
      "ApplicationAttachment": {
        "description": "Attachment linked to an application (resume/CV, cover letter, signed documents).",
        "allOf": [
          {
            "$ref": "#/components/schemas/ApiAttachment"
          }
        ]
      },
      "ApplicationAttachmentUploadRequest": {
        "type": "object",
        "required": [
          "file"
        ],
        "properties": {
          "file": {
            "$ref": "#/components/schemas/FileData"
          }
        },
        "additionalProperties": false
      },
      "UploadApiAttachmentRequest": {
        "type": "object",
        "required": [
          "category",
          "file"
        ],
        "properties": {
          "category": {
            "type": "string",
            "enum": [
              "voicemail",
              "candidate",
              "application",
              "candidate_comment",
              "job_note",
              "company_favicon",
              "company_header",
              "company_link_preview"
            ],
            "description": "Attachment category. Determines file-type validation rules and `object_id` requirements."
          },
          "company_id": {
            "type": "integer",
            "nullable": true,
            "description": "Target company ID. Required only for partner API keys that manage multiple client companies — pick the company the attachment belongs to. If omitted, defaults to the authenticated company. The attachment is stored under this company, and the referenced `object_id` (when present) MUST belong to this same company — mismatch returns 404."
          },
          "object_id": {
            "type": "integer",
            "nullable": true,
            "description": "Target object ID. Required for every category except `voicemail`. Resolves to candidate/application/comment/job-note/company per category. The object's company is strictly matched against `company_id` (or authenticated company when `company_id` omitted); no cross-company uploads."
          },
          "file": {
            "$ref": "#/components/schemas/FileData"
          }
        },
        "additionalProperties": false
      },
      "ApplicationCvData": {
        "description": "Application CV. Returns standard attachment metadata + download URL. When `?include=cv.text` is requested, a `text` field with parsed plain-text content is added.",
        "allOf": [
          {
            "$ref": "#/components/schemas/ApiAttachment"
          },
          {
            "type": "object",
            "properties": {
              "text": {
                "type": "string",
                "nullable": true,
                "description": "Parsed plain-text CV content. Included only when `?include=cv.text` is requested AND `view=full` (the default). Suppressed when `view=summary` even if the include was requested — parsed CV text can be tens of KB per attachment. May be null if parsing fails or format is unsupported."
              }
            }
          }
        ]
      },
      "JobLocation": {
        "type": "object",
        "properties": {
          "country": {
            "type": "string",
            "description": "Country."
          },
          "city": {
            "type": "string",
            "description": "City."
          },
          "state": {
            "type": "string",
            "description": "State or region."
          },
          "postal_code": {
            "type": "string",
            "description": "Postal code."
          },
          "street_address": {
            "type": "string",
            "description": "Street address."
          },
          "full_address": {
            "type": "string",
            "description": "Full formatted address."
          }
        }
      },
      "JobHiringTeamMember": {
        "type": "object",
        "required": [
          "id",
          "full_name"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "User ID."
          },
          "full_name": {
            "type": "string",
            "description": "User full name."
          },
          "email": {
            "type": [
              "string",
              "null"
            ],
            "description": "User email."
          },
          "role": {
            "type": [
              "string",
              "null"
            ],
            "description": "Role on hiring team (e.g. hiring_manager, recruiter)."
          }
        }
      },
      "Job": {
        "type": "object",
        "required": [
          "id",
          "company_id",
          "title",
          "status",
          "url",
          "is_remote",
          "created_at",
          "updated_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "alias": {
            "type": [
              "string",
              "null"
            ],
            "description": "Short alphanumeric alias used in UI URLs. Use this to build job links — `https://app.100hires.com/job/{alias}/candidates/pipeline`. Also accepted as `{id}` in API requests.",
            "example": "79SZHfT"
          },
          "company_id": {
            "type": "integer",
            "description": "ID of the company this job belongs to"
          },
          "title": {
            "type": "string",
            "description": "Public job title shown to candidates"
          },
          "internal_title": {
            "type": [
              "string",
              "null"
            ],
            "description": "Internal job title visible only to the hiring team"
          },
          "internal_job_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Company's internal job identifier (e.g. requisition number)"
          },
          "description": {
            "type": "string",
            "description": "Job description (HTML). Present only when `view=full` (default); omitted entirely when `view=summary` to keep list responses inside the agent context budget. Use `GET /jobs/{id}` or `view=full` to retrieve."
          },
          "resume_field_status": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "required",
              "optional",
              "hidden"
            ],
            "description": "Whether resume upload is required, optional, or hidden on the application form"
          },
          "location": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/JobLocation"
              },
              {
                "type": "null"
              }
            ],
            "description": "Job location details"
          },
          "url": {
            "type": "string",
            "description": "Public URL of the job posting page"
          },
          "url_backoffice": {
            "type": "string",
            "description": "Backoffice URL — opens the job's pipeline view inside the recruiter app (`https://app.100hires.com/job/{alias}/candidates/pipeline`). Use this to link agent widgets / UI to the in-app job page rather than the public career page."
          },
          "is_remote": {
            "type": "boolean",
            "description": "Whether this is a remote position"
          },
          "status": {
            "type": "string",
            "description": "Job status: open, closed, draft, or archived"
          },
          "department": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Department this job belongs to"
          },
          "category": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Job category (e.g. Engineering, Marketing)"
          },
          "employment_type": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Employment type (e.g. Full-time, Part-time, Contract)"
          },
          "education_level": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Required education level"
          },
          "experience_level": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Required experience level (e.g. Entry, Mid, Senior)"
          },
          "workflow_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "ID of the hiring workflow (pipeline) assigned to this job"
          },
          "workflow": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/IdName"
              },
              {
                "type": "null"
              }
            ],
            "description": "Hiring workflow (pipeline) assigned to this job. Embedded via `include=workflow`. Suppressed when `view=summary` even if the include was requested."
          },
          "pipeline_stages": {
            "oneOf": [
              {
                "type": "array",
                "items": {
                  "type": "object",
                  "properties": {
                    "id": {
                      "type": "integer"
                    },
                    "name": {
                      "type": "string"
                    }
                  }
                }
              },
              {
                "type": "null"
              }
            ],
            "description": "Pipeline stages for this job's workflow. Only included when `include=pipeline_stages` is specified. Suppressed when `view=summary` even if the include was requested."
          },
          "salary_min": {
            "type": [
              "number",
              "null"
            ],
            "description": "Minimum salary"
          },
          "salary_max": {
            "type": [
              "number",
              "null"
            ],
            "description": "Maximum salary"
          },
          "salary_currency": {
            "type": [
              "string",
              "null"
            ],
            "description": "Salary currency code (e.g. USD, EUR)"
          },
          "salary_period": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "annually",
              "monthly",
              "daily",
              "hourly"
            ],
            "description": "Salary period"
          },
          "hours_per_week_min": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Minimum hours per week"
          },
          "hours_per_week_max": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Maximum hours per week"
          },
          "indeed_posting_data": {
            "type": "object",
            "additionalProperties": true,
            "description": "Indeed job board posting metadata. Present only when `view=full` (default); omitted entirely when `view=summary`."
          },
          "hiring_team": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/JobHiringTeamMember"
            },
            "description": "Team members assigned to this job. Embedded via `include=hiring_team`. Suppressed when `view=summary` even if the include was requested."
          },
          "is_satellite": {
            "type": "boolean",
            "description": "Whether this job is a satellite (child) of a canonical job. Satellite jobs share the candidate pipeline of their parent."
          },
          "parent_job_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "ID of the canonical (parent) job. Null for canonical jobs. Recruiting operations should target the canonical job."
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "ai_scoring_criteria": {
            "type": "array",
            "description": "AI scoring criteria configured for this job, ordered by `position` ASC. Returned as an empty array when none are configured. Present only when `view=full` (default); omitted entirely when `view=summary`.",
            "items": {
              "$ref": "#/components/schemas/AiScoringCriterion"
            }
          }
        }
      },
      "AiScoringCriterion": {
        "type": "object",
        "required": [
          "id",
          "text",
          "weight",
          "position"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier of the criterion."
          },
          "title": {
            "type": [
              "string",
              "null"
            ],
            "description": "Optional short label for the criterion."
          },
          "text": {
            "type": "string",
            "description": "Prompt text describing what to evaluate."
          },
          "weight": {
            "type": "integer",
            "minimum": 1,
            "maximum": 10,
            "description": "Relative importance of this criterion in the total score (1–10)."
          },
          "position": {
            "type": "integer",
            "description": "0-based ordinal of the criterion in the job's list."
          }
        }
      },
      "AiScoringCriterionInput": {
        "type": "object",
        "required": [
          "text",
          "weight"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "ID of an existing criterion attached to this job. When present, the\ncorresponding criterion is updated in place (or, if it has scores,\ndetached and replaced — `ManageCriteria::createOrUpdate` semantics).\nOmit `id` to create a new criterion. Items existing on the job that\nare not present in the request (matched by `id`) are removed\n(soft-deleted if unscored, detached if used in past evaluations).\n"
          },
          "title": {
            "type": "string",
            "description": "Optional short label for the criterion."
          },
          "text": {
            "type": "string",
            "description": "Prompt text describing what to evaluate. Required."
          },
          "weight": {
            "type": "integer",
            "minimum": 1,
            "maximum": 10,
            "description": "Relative importance of this criterion in the total score (1–10)."
          }
        }
      },
      "JobListResponse": {
        "type": "object",
        "required": [
          "jobs",
          "pagination"
        ],
        "properties": {
          "jobs": {
            "type": "array",
            "description": "Array of jobs.",
            "items": {
              "$ref": "#/components/schemas/Job"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "JobCreateRequest": {
        "type": "object",
        "required": [
          "status",
          "title",
          "description",
          "location_city",
          "location_country"
        ],
        "properties": {
          "company_id": {
            "type": "integer",
            "description": "Target company ID. Required only when the API key has access to multiple companies."
          },
          "form_id": {
            "type": "integer",
            "description": "Application form ID. If omitted, a new form named after the job title is created with default questions (First name, Last name, Email, Phone)."
          },
          "status": {
            "type": "string",
            "description": "Job status (e.g. Draft, Public). See GET /taxonomy/statuses."
          },
          "title": {
            "type": "string",
            "description": "Public job title."
          },
          "internal_title": {
            "type": "string",
            "description": "Internal-only title visible to the hiring team."
          },
          "internal_job_id": {
            "type": "string",
            "description": "External reference ID from your ATS or HR system."
          },
          "description": {
            "type": "string",
            "description": "Job description (HTML allowed)."
          },
          "resume_field_status": {
            "type": "string",
            "description": "Resume field behavior on the application form.",
            "enum": [
              "required",
              "optional",
              "hidden"
            ]
          },
          "location_city": {
            "type": "string",
            "description": "Job city."
          },
          "location_country": {
            "type": "string",
            "description": "Job country."
          },
          "location_state": {
            "type": "string",
            "description": "Job state or region."
          },
          "location_street_address": {
            "type": "string",
            "description": "Street address."
          },
          "location_full_address": {
            "type": "string",
            "description": "Full formatted address."
          },
          "location_postal_code": {
            "type": "string",
            "description": "Postal or ZIP code."
          },
          "salary_min": {
            "type": "number",
            "description": "Minimum salary."
          },
          "salary_max": {
            "type": "number",
            "description": "Maximum salary."
          },
          "salary_currency": {
            "type": "string",
            "description": "Salary currency code (e.g. USD, EUR)."
          },
          "salary_period": {
            "type": "string",
            "description": "Salary period.",
            "enum": [
              "annually",
              "monthly",
              "daily",
              "hourly"
            ]
          },
          "is_remote": {
            "type": "boolean",
            "description": "Whether this is a remote position."
          },
          "employment_type_id": {
            "type": "integer",
            "description": "Employment type ID from GET /taxonomy/employment-types."
          },
          "department_id": {
            "type": "integer",
            "description": "Department ID from GET /taxonomy/departments."
          },
          "category_id": {
            "type": "integer",
            "description": "Job category ID from GET /taxonomy/categories."
          },
          "education_level_id": {
            "type": "integer",
            "description": "Education level ID from GET /taxonomy/education-levels."
          },
          "experience_level_id": {
            "type": "integer",
            "description": "Experience level ID from GET /taxonomy/experience-levels."
          },
          "workflow_id": {
            "type": "integer",
            "description": "Workflow ID. If omitted, a new workflow named after the job title is created with default stages."
          },
          "parent_job_id": {
            "type": "integer",
            "description": "Canonical parent job ID. If provided, the created job becomes a satellite job."
          },
          "knockout_questions": {
            "type": "array",
            "description": "Boolean knockout questions added to the application form. Each question with `disqualify_on_wrong_answer=true` creates an auto-disqualify rule on the Applied stage.",
            "items": {
              "type": "object",
              "required": [
                "text",
                "expected_answer",
                "disqualify_on_wrong_answer"
              ],
              "properties": {
                "text": {
                  "type": "string",
                  "description": "Question text shown to the applicant."
                },
                "expected_answer": {
                  "type": "string",
                  "enum": [
                    "Yes",
                    "No"
                  ],
                  "description": "The correct/desired answer."
                },
                "disqualify_on_wrong_answer": {
                  "type": "boolean",
                  "description": "If true, applicants who answer incorrectly are automatically disqualified."
                }
              }
            }
          },
          "ai_scoring_criteria": {
            "type": "array",
            "description": "AI scoring criteria for evaluating candidates against this job.\nProviding this field is a full replace: existing criteria are detached\n(preserved if used in past evaluations, soft-deleted otherwise) and the\nsupplied list becomes the current set. Omit the field to leave defaults\nuntouched. Pass an empty array to detach all criteria.\n",
            "items": {
              "$ref": "#/components/schemas/AiScoringCriterionInput"
            }
          }
        },
        "additionalProperties": false
      },
      "JobUpdateRequest": {
        "type": "object",
        "properties": {
          "form_id": {
            "type": "integer",
            "description": "Application form ID to assign to this job."
          },
          "status": {
            "type": "string",
            "description": "Job status (e.g. Draft, Public). See GET /taxonomy/statuses."
          },
          "title": {
            "type": "string",
            "description": "Public job title."
          },
          "internal_title": {
            "type": "string",
            "description": "Internal-only title visible to the hiring team."
          },
          "internal_job_id": {
            "type": "string",
            "description": "External reference ID from your ATS or HR system."
          },
          "description": {
            "type": "string",
            "description": "Job description (HTML allowed)."
          },
          "resume_field_status": {
            "type": "string",
            "description": "Resume field behavior on the application form.",
            "enum": [
              "required",
              "optional",
              "hidden"
            ]
          },
          "location_city": {
            "type": "string",
            "description": "Job city."
          },
          "location_country": {
            "type": "string",
            "description": "Job country."
          },
          "location_state": {
            "type": "string",
            "description": "Job state or region."
          },
          "location_street_address": {
            "type": "string",
            "description": "Street address."
          },
          "location_full_address": {
            "type": "string",
            "description": "Full formatted address."
          },
          "location_postal_code": {
            "type": "string",
            "description": "Postal or ZIP code."
          },
          "salary_min": {
            "type": "number",
            "description": "Minimum salary."
          },
          "salary_max": {
            "type": "number",
            "description": "Maximum salary."
          },
          "salary_currency": {
            "type": "string",
            "description": "Salary currency code (e.g. USD, EUR)."
          },
          "salary_period": {
            "type": "string",
            "description": "Salary period.",
            "enum": [
              "annually",
              "monthly",
              "daily",
              "hourly"
            ]
          },
          "is_remote": {
            "type": "boolean",
            "description": "Whether this is a remote position."
          },
          "employment_type_id": {
            "type": "integer",
            "description": "Employment type ID from GET /taxonomy/employment-types."
          },
          "department_id": {
            "type": "integer",
            "description": "Department ID from GET /taxonomy/departments."
          },
          "category_id": {
            "type": "integer",
            "description": "Job category ID from GET /taxonomy/categories."
          },
          "education_level_id": {
            "type": "integer",
            "description": "Education level ID from GET /taxonomy/education-levels."
          },
          "experience_level_id": {
            "type": "integer",
            "description": "Experience level ID from GET /taxonomy/experience-levels."
          },
          "workflow_id": {
            "type": "integer",
            "description": "Workflow ID to assign to this job."
          },
          "parent_job_id": {
            "type": "integer",
            "description": "Canonical parent job ID. If provided, the job becomes a satellite job."
          },
          "knockout_questions": {
            "type": "array",
            "description": "Boolean knockout questions added to the application form. Each question with `disqualify_on_wrong_answer=true` creates an auto-disqualify rule on the Applied stage.",
            "items": {
              "type": "object",
              "required": [
                "text",
                "expected_answer",
                "disqualify_on_wrong_answer"
              ],
              "properties": {
                "text": {
                  "type": "string",
                  "description": "Question text shown to the applicant."
                },
                "expected_answer": {
                  "type": "string",
                  "enum": [
                    "Yes",
                    "No"
                  ],
                  "description": "The correct/desired answer."
                },
                "disqualify_on_wrong_answer": {
                  "type": "boolean",
                  "description": "If true, applicants who answer incorrectly are automatically disqualified."
                }
              }
            }
          },
          "ai_scoring_criteria": {
            "type": "array",
            "description": "AI scoring criteria for evaluating candidates against this job.\nDiff-replace by `id`: items with `id` update the matching existing\ncriterion (preserving identity), items without `id` create new\ncriteria, and existing criteria not referenced in the payload are\nremoved. Omit the field to leave existing criteria untouched. Pass\nan empty array to detach all criteria. Each item's order in the\narray becomes its `position`.\n",
            "items": {
              "$ref": "#/components/schemas/AiScoringCriterionInput"
            }
          }
        },
        "additionalProperties": false
      },
      "JobStatusUpdateRequest": {
        "type": "object",
        "required": [
          "status"
        ],
        "properties": {
          "status": {
            "type": "string",
            "description": "New job status (e.g. Draft, Public, Archived). See GET /taxonomy/statuses."
          }
        },
        "additionalProperties": false
      },
      "HiringTeamAddRequest": {
        "type": "object",
        "required": [
          "user_id"
        ],
        "properties": {
          "user_id": {
            "type": "integer",
            "description": "User ID to add to the hiring team."
          }
        },
        "additionalProperties": false
      },
      "HiringTeamResponse": {
        "type": "object",
        "required": [
          "hiring_team"
        ],
        "properties": {
          "hiring_team": {
            "type": "array",
            "description": "Array of hiring team members.",
            "items": {
              "$ref": "#/components/schemas/JobHiringTeamMember"
            }
          }
        }
      },
      "Webhook": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "url": {
            "type": "string",
            "description": "Endpoint URL that receives webhook event payloads"
          }
        }
      },
      "WebhookWithSecret": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "url": {
            "type": "string",
            "description": "Endpoint URL that receives webhook event payloads"
          },
          "signing_secret": {
            "type": "string",
            "description": "HMAC-SHA256 signing secret for this webhook, used to verify the `x-hires-signature-v2` header. Returned ONLY in create and rotate-secret responses — store it securely, it is never shown again."
          }
        }
      },
      "WebhookListResponse": {
        "type": "object",
        "required": [
          "webhooks",
          "pagination"
        ],
        "properties": {
          "webhooks": {
            "type": "array",
            "description": "Array of webhooks.",
            "items": {
              "$ref": "#/components/schemas/Webhook"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "WebhookCreateRequest": {
        "type": "object",
        "required": [
          "url"
        ],
        "properties": {
          "url": {
            "type": "string",
            "description": "Webhook destination URL. Must be HTTPS.",
            "maxLength": 2048
          }
        },
        "additionalProperties": false
      },
      "JobBoardsMutationRequest": {
        "type": "object",
        "properties": {
          "boards": {
            "type": "array",
            "description": "Array of board IDs to activate or deactivate.",
            "items": {
              "type": "string"
            }
          }
        },
        "additionalProperties": false
      },
      "JobBoardItem": {
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Board identifier."
          },
          "title": {
            "type": "string",
            "description": "Board display name."
          },
          "indeed_posting_url": {
            "type": "string",
            "nullable": true,
            "description": "Public Indeed posting URL when the job has been sourced/posted to Indeed; null otherwise. Populated only for the Indeed board."
          },
          "ziprecruiter_posting_url": {
            "type": "string",
            "nullable": true,
            "description": "Public ZipRecruiter posting URL (the API `preview_url`) when the job has been posted to ZipRecruiter; null otherwise. Populated only for the ZipRecruiter board."
          }
        }
      },
      "JobBoardsResponse": {
        "type": "object",
        "required": [
          "boards"
        ],
        "properties": {
          "boards": {
            "type": "array",
            "description": "Array of job boards for this job.",
            "items": {
              "$ref": "#/components/schemas/JobBoardItem"
            }
          }
        }
      },
      "BatchJobBoardsRequest": {
        "type": "object",
        "required": [
          "jobs"
        ],
        "properties": {
          "jobs": {
            "type": "array",
            "description": "Array of job IDs.",
            "items": {
              "type": "integer"
            }
          },
          "boards": {
            "type": "array",
            "description": "Array of board IDs.",
            "items": {
              "type": "string"
            }
          }
        },
        "additionalProperties": false
      },
      "BatchJobBoardsResponse": {
        "type": "object",
        "required": [
          "jobs"
        ],
        "properties": {
          "jobs": {
            "type": "array",
            "description": "Array of per-job board results.",
            "items": {
              "type": "object",
              "required": [
                "job_id",
                "boards"
              ],
              "properties": {
                "job_id": {
                  "type": "integer"
                },
                "boards": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/JobBoardItem"
                  }
                }
              }
            }
          }
        }
      },
      "BatchMoveApplicationsRequest": {
        "type": "object",
        "required": [
          "ids",
          "stage_id"
        ],
        "properties": {
          "ids": {
            "type": "array",
            "items": {
              "type": "integer"
            },
            "maxItems": 100,
            "description": "Application IDs to move (max 100)"
          },
          "stage_id": {
            "type": "integer",
            "description": "Target pipeline stage ID"
          }
        },
        "additionalProperties": false
      },
      "BatchRejectApplicationsRequest": {
        "type": "object",
        "required": [
          "ids"
        ],
        "properties": {
          "ids": {
            "type": "array",
            "items": {
              "type": "integer"
            },
            "maxItems": 100,
            "description": "Application IDs to reject (max 100)"
          },
          "rejection_reason_id": {
            "type": "integer",
            "description": "Optional rejection reason ID"
          }
        },
        "additionalProperties": false
      },
      "BatchTagsCandidatesRequest": {
        "type": "object",
        "required": [
          "ids",
          "tags"
        ],
        "properties": {
          "ids": {
            "type": "array",
            "items": {
              "type": "integer"
            },
            "maxItems": 100,
            "description": "Candidate IDs to tag (max 100)"
          },
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Tag names to attach"
          }
        },
        "additionalProperties": false
      },
      "BatchResultResponse": {
        "type": "object",
        "required": [
          "results"
        ],
        "properties": {
          "results": {
            "type": "array",
            "description": "Array of per-item results.",
            "items": {
              "$ref": "#/components/schemas/BatchResultItem"
            }
          }
        }
      },
      "BatchResultItem": {
        "type": "object",
        "required": [
          "id"
        ],
        "properties": {
          "id": {
            "oneOf": [
              {
                "type": "integer"
              },
              {
                "type": "string"
              }
            ],
            "description": "Entity ID or alias from the request"
          },
          "data": {
            "type": "object",
            "description": "Entity payload on success. Present only when the item succeeded."
          },
          "error": {
            "type": "object",
            "description": "Structured error object on failure. Present only when the item failed. Same format as top-level API errors.",
            "properties": {
              "name": {
                "type": "string",
                "example": "Not Found"
              },
              "message": {
                "type": "string",
                "example": "Candidate not found"
              },
              "code": {
                "type": "integer",
                "example": 0
              },
              "status": {
                "type": "integer",
                "example": 404
              },
              "validation_errors": {
                "type": "object",
                "additionalProperties": {
                  "type": "string"
                }
              }
            }
          }
        }
      },
      "BatchCreateMessagesRequest": {
        "type": "object",
        "required": [
          "messages"
        ],
        "properties": {
          "messages": {
            "type": "array",
            "maxItems": 100,
            "description": "Array of message payloads to create (max 100).",
            "items": {
              "allOf": [
                {
                  "type": "object",
                  "required": [
                    "candidate_id"
                  ],
                  "properties": {
                    "candidate_id": {
                      "type": "integer",
                      "description": "Target candidate ID for this message."
                    }
                  }
                },
                {
                  "$ref": "#/components/schemas/ScheduledEmailCreateRequest"
                }
              ]
            }
          }
        },
        "additionalProperties": false
      },
      "BatchCreateMessagesResponse": {
        "type": "object",
        "required": [
          "results"
        ],
        "properties": {
          "results": {
            "type": "array",
            "description": "Array of per-message results with success or error details.",
            "items": {
              "$ref": "#/components/schemas/BatchCreateMessagesResultItem"
            }
          }
        }
      },
      "BatchCreateMessagesResultItem": {
        "type": "object",
        "required": [
          "index",
          "candidate_id"
        ],
        "properties": {
          "index": {
            "type": "integer",
            "description": "Zero-based index of this item in the request array."
          },
          "candidate_id": {
            "type": "integer",
            "nullable": true,
            "description": "Candidate ID from the request. Null if not provided."
          },
          "data": {
            "$ref": "#/components/schemas/ScheduledEmail",
            "description": "Created message payload on success. Present only when the item succeeded."
          },
          "error": {
            "type": "object",
            "description": "Structured error object on failure. Present only when the item failed. Same format as top-level API errors.",
            "properties": {
              "name": {
                "type": "string",
                "example": "Not Found"
              },
              "message": {
                "type": "string",
                "example": "Candidate not found"
              },
              "code": {
                "type": "integer",
                "example": 0
              },
              "status": {
                "type": "integer",
                "example": 404
              },
              "validation_errors": {
                "type": "object",
                "additionalProperties": {
                  "type": "string"
                }
              }
            }
          }
        }
      },
      "EvaluationListResponse": {
        "type": "object",
        "required": [
          "evaluations"
        ],
        "properties": {
          "evaluations": {
            "type": "array",
            "description": "Array of evaluation summaries.",
            "items": {
              "$ref": "#/components/schemas/EvaluationSummary"
            }
          }
        }
      },
      "EvaluationSummary": {
        "type": "object",
        "required": [
          "id",
          "application_id",
          "form_id",
          "form_name",
          "user",
          "summary_score",
          "created_at",
          "updated_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Evaluation form ID."
          },
          "application_id": {
            "type": "integer",
            "description": "Application ID."
          },
          "form_id": {
            "type": "integer",
            "description": "Source form template ID."
          },
          "form_name": {
            "type": "string",
            "description": "Form name."
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL of the candidate's evaluations tab in the 100Hires recruiter app where this evaluation appears. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/candidate/dtGeby2#/profile/evaluations"
          },
          "form_url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL to edit the source evaluation form template in the 100Hires recruiter app.",
            "example": "https://app.100hires.com/settings/evaluation/abc123/edit"
          },
          "user": {
            "type": "object",
            "description": "Evaluator details.",
            "properties": {
              "id": {
                "type": "integer"
              },
              "full_name": {
                "type": "string"
              }
            }
          },
          "summary_score": {
            "type": "string",
            "description": "Average score.",
            "enum": [
              "strong-yes",
              "probably-yes",
              "neutral",
              "probably-no",
              "strong-no"
            ]
          },
          "summary_text": {
            "type": [
              "string",
              "null"
            ],
            "description": "Evaluator summary. Present only when `view=full` (default); replaced with `summary_text_preview` when `view=summary`."
          },
          "summary_text_preview": {
            "type": [
              "string",
              "null"
            ],
            "description": "First 200 UTF-8 characters of the evaluator summary with a `...` suffix when truncated. Present only when `view=summary`; replaces `summary_text` to keep list responses inside the agent context budget."
          },
          "created_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          }
        }
      },
      "EvaluationDetail": {
        "allOf": [
          {
            "$ref": "#/components/schemas/EvaluationSummary"
          },
          {
            "type": "object",
            "required": [
              "answers"
            ],
            "properties": {
              "answers": {
                "type": "array",
                "items": {
                  "$ref": "#/components/schemas/EvaluationAnswer"
                }
              }
            }
          }
        ]
      },
      "EvaluationAnswer": {
        "type": "object",
        "required": [
          "question_id",
          "question_text",
          "value"
        ],
        "properties": {
          "question_id": {
            "type": "integer",
            "description": "Question ID."
          },
          "question_text": {
            "type": "string",
            "description": "Question text."
          },
          "value": {
            "type": [
              "string",
              "null"
            ],
            "description": "Answer value. Null if unanswered."
          }
        }
      },
      "Company": {
        "type": "object",
        "required": [
          "id",
          "name"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "name": {
            "type": "string",
            "description": "Company name"
          },
          "website": {
            "type": [
              "string",
              "null"
            ],
            "description": "Company website URL"
          },
          "url": {
            "type": [
              "string",
              "null"
            ],
            "description": "Company careers page URL"
          },
          "is_staffing_agency": {
            "type": "boolean",
            "description": "Whether this company is a staffing agency"
          },
          "logo": {
            "type": [
              "string",
              "null"
            ],
            "description": "URL of the company logo image"
          },
          "company_owner_email": {
            "type": [
              "string",
              "null"
            ],
            "description": "Email of the company owner"
          },
          "company_owner_phone": {
            "type": [
              "string",
              "null"
            ],
            "description": "Phone number of the company owner"
          },
          "company_owner_name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Full name of the company owner"
          }
        }
      },
      "CompanyListResponse": {
        "type": "object",
        "required": [
          "companies",
          "pagination"
        ],
        "properties": {
          "companies": {
            "type": "array",
            "description": "Array of companies.",
            "items": {
              "$ref": "#/components/schemas/Company"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "CompanyCreateRequest": {
        "type": "object",
        "required": [
          "name",
          "company_owner_email",
          "company_owner_name"
        ],
        "properties": {
          "name": {
            "type": "string",
            "description": "Company name."
          },
          "website": {
            "type": "string",
            "description": "Company website URL."
          },
          "url": {
            "type": "string",
            "description": "Company profile URL."
          },
          "company_owner_email": {
            "type": "string",
            "format": "email",
            "description": "Company owner email address."
          },
          "company_owner_name": {
            "type": "string",
            "description": "Company owner full name."
          },
          "company_owner_phone": {
            "type": "string",
            "description": "Company owner phone number."
          },
          "is_staffing_agency": {
            "type": "boolean",
            "description": "Whether this company is a staffing agency."
          },
          "logo": {
            "$ref": "#/components/schemas/FileData"
          }
        },
        "additionalProperties": false
      },
      "CompanyUpdateRequest": {
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Company name."
          },
          "website": {
            "type": "string",
            "description": "Company website URL."
          },
          "url": {
            "type": "string",
            "description": "Company profile URL."
          },
          "company_owner_email": {
            "type": "string",
            "format": "email",
            "description": "Company owner email address."
          },
          "company_owner_name": {
            "type": "string",
            "description": "Company owner full name."
          },
          "company_owner_phone": {
            "type": "string",
            "description": "Company owner phone number."
          },
          "is_staffing_agency": {
            "type": "boolean",
            "description": "Whether this company is a staffing agency."
          },
          "logo": {
            "$ref": "#/components/schemas/FileData"
          }
        },
        "additionalProperties": false
      },
      "NoteUser": {
        "type": "object",
        "required": [
          "id",
          "full_name"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "User ID."
          },
          "full_name": {
            "type": "string",
            "description": "User full name."
          },
          "photo": {
            "type": [
              "string",
              "null"
            ],
            "description": "Profile photo URL."
          }
        }
      },
      "Note": {
        "type": "object",
        "required": [
          "id",
          "candidate_id",
          "user_id",
          "visibility",
          "created_at",
          "updated_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "candidate_id": {
            "type": "integer",
            "description": "ID of the candidate this note belongs to"
          },
          "user_id": {
            "type": "integer",
            "description": "Author user ID (always present)"
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL to the candidate's discussion tab where this note appears in the 100Hires recruiter app. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/candidate/dtGeby2#/profile/discussion"
          },
          "body": {
            "type": "string",
            "description": "Note content (may contain HTML). Mentioned users are wrapped in `<span class=\"mention-area\">` markup. Present only when `view=full` (default); replaced with `body_preview` when `view=summary`."
          },
          "body_preview": {
            "type": "string",
            "description": "First 200 UTF-8 characters of the note content with a `...` suffix when truncated. Present only when `view=summary`; replaces `body` to keep list responses inside the agent context budget."
          },
          "visibility": {
            "type": "string",
            "description": "Visibility: 'all' (visible to team) or 'private' (author only)"
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "user": {
            "description": "Author details (only with include=user)",
            "allOf": [
              {
                "$ref": "#/components/schemas/NoteUser"
              }
            ]
          },
          "candidate": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/Candidate"
              },
              {
                "type": "null"
              }
            ],
            "description": "Embedded candidate payload (included when requested via `include=candidate`). Use `candidate.url_backoffice` to deep-link UI widgets to the candidate profile in the recruiter app."
          }
        }
      },
      "NoteListResponse": {
        "type": "object",
        "required": [
          "notes",
          "pagination"
        ],
        "properties": {
          "notes": {
            "type": "array",
            "description": "Array of notes.",
            "items": {
              "$ref": "#/components/schemas/Note"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "NoteCreateRequest": {
        "type": "object",
        "required": [
          "candidate_id",
          "body"
        ],
        "properties": {
          "candidate_id": {
            "type": "string",
            "pattern": "^[A-Za-z0-9_-]+$",
            "description": "Candidate ID (numeric) or alias"
          },
          "body": {
            "type": "string",
            "description": "Note content. Supports HTML."
          },
          "user_id": {
            "type": "integer",
            "description": "Author user ID. If omitted, the authenticated user is used"
          },
          "visibility": {
            "type": "string",
            "description": "Visibility: 'all' (default) or 'private'"
          },
          "mention_user_ids": {
            "type": "array",
            "items": {
              "type": "integer"
            },
            "description": "Array of user IDs to mention. Mentioned users receive email notifications and their `@name` or `@login` references in the body are replaced with HTML mention markup."
          }
        },
        "additionalProperties": false
      },
      "NoteUpdateRequest": {
        "type": "object",
        "properties": {
          "body": {
            "type": "string",
            "description": "Note content. Supports HTML."
          },
          "visibility": {
            "type": "string",
            "description": "Visibility: 'all' (default) or 'private'."
          }
        },
        "additionalProperties": false
      },
      "Question": {
        "type": "object",
        "required": [
          "id",
          "text",
          "type"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Question ID."
          },
          "text": {
            "type": "string",
            "description": "Question text."
          },
          "type": {
            "type": "string",
            "description": "Question type."
          },
          "options": {
            "type": "array",
            "description": "Answer options for select/multiselect types.",
            "items": {
              "type": "string"
            }
          },
          "status": {
            "type": "string",
            "description": "Visibility status on the form.",
            "enum": [
              "required",
              "optional",
              "hidden"
            ]
          }
        }
      },
      "Form": {
        "type": "object",
        "required": [
          "id",
          "name"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Form ID."
          },
          "name": {
            "type": "string",
            "description": "Form name."
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL to edit this questionnaire form in the 100Hires recruiter app. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/settings/forms/42/edit"
          },
          "questions": {
            "type": "array",
            "description": "Array of questions on this form. Present only when `view=full` (default); omitted entirely when `view=summary` — forms can embed dozens of question definitions.",
            "items": {
              "$ref": "#/components/schemas/Question"
            }
          }
        }
      },
      "FormListResponse": {
        "type": "object",
        "required": [
          "forms",
          "pagination"
        ],
        "properties": {
          "forms": {
            "type": "array",
            "description": "Array of forms.",
            "items": {
              "$ref": "#/components/schemas/Form"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "FormCreateRequest": {
        "type": "object",
        "required": [
          "name"
        ],
        "properties": {
          "company_id": {
            "type": "integer",
            "description": "Target company ID."
          },
          "name": {
            "type": "string",
            "description": "Form name."
          },
          "questions": {
            "type": "array",
            "description": "Array of question IDs to attach to this form.",
            "items": {
              "type": "integer"
            }
          }
        },
        "additionalProperties": false
      },
      "FormUpdateRequest": {
        "type": "object",
        "required": [
          "name"
        ],
        "properties": {
          "name": {
            "type": "string",
            "description": "Form name."
          },
          "questions": {
            "type": "array",
            "description": "Array of question IDs to attach to this form.",
            "items": {
              "type": "integer"
            }
          }
        },
        "additionalProperties": false
      },
      "FormQuestionStatusRequest": {
        "type": "object",
        "required": [
          "status"
        ],
        "properties": {
          "status": {
            "type": "string",
            "description": "Question visibility on this form: required, optional, or hidden.",
            "enum": [
              "required",
              "optional",
              "hidden"
            ]
          }
        },
        "additionalProperties": false
      },
      "EmailTemplate": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Email template ID"
          },
          "name": {
            "type": "string",
            "description": "Template name"
          },
          "subject": {
            "type": "string",
            "description": "Email subject line as stored. Placeholders, when present, are stored as `<tag>` HTML produced by `POST /template-placeholders/prepare`; they are rendered to real values only at send time, not on read.\n"
          },
          "body": {
            "type": "string",
            "description": "Email body HTML as stored. Placeholders are stored as `<tag>` HTML produced by `POST /template-placeholders/prepare` and rendered at send time. Present only when `view=full` (default); omitted entirely when `view=summary` — template bodies can be tens of KB each.\n"
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL to edit this email template in the 100Hires recruiter app. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/settings/message-templates/edit?id=42"
          },
          "created_at": {
            "type": "integer",
            "description": "Unix timestamp"
          },
          "updated_at": {
            "type": "integer",
            "description": "Unix timestamp"
          }
        }
      },
      "EmailTemplateListResponse": {
        "type": "object",
        "required": [
          "email_templates",
          "pagination"
        ],
        "properties": {
          "email_templates": {
            "type": "array",
            "description": "Array of email templates.",
            "items": {
              "$ref": "#/components/schemas/EmailTemplate"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "EmailTemplateCreateRequest": {
        "type": "object",
        "required": [
          "name",
          "subject",
          "body"
        ],
        "properties": {
          "company_id": {
            "type": "integer",
            "description": "Target company ID."
          },
          "name": {
            "type": "string",
            "description": "Template name"
          },
          "subject": {
            "type": "string",
            "description": "Email subject line. Plain text.\n\n**Placeholders:** literal `{{first_name}}` / `{{job_title}}` tokens are NOT substituted — they will be delivered to the recipient verbatim. To embed a placeholder, call `POST /template-placeholders/prepare` and paste the returned HTML `<tag>…</tag>` string into this field.\n"
          },
          "body": {
            "type": "string",
            "description": "Email body HTML.\n\n**Placeholders:** literal `{{first_name}}` tokens are NOT substituted — the recipient will see the raw text. To embed a placeholder, call `POST /template-placeholders/prepare` and insert the returned `<tag contenteditable=\"false\" data-type=\"…\" data-identifier=\"…\">…</tag>` element into the HTML at the position where the value should appear.\n"
          }
        },
        "additionalProperties": false
      },
      "EmailTemplateUpdateRequest": {
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Template name"
          },
          "subject": {
            "type": "string",
            "description": "Email subject line. Plain text.\n\n**Placeholders:** literal `{{first_name}}` / `{{job_title}}` tokens are NOT substituted — they will be delivered to the recipient verbatim. To embed a placeholder, call `POST /template-placeholders/prepare` and paste the returned HTML `<tag>…</tag>` string into this field.\n"
          },
          "body": {
            "type": "string",
            "description": "Email body HTML.\n\n**Placeholders:** literal `{{first_name}}` tokens are NOT substituted — the recipient will see the raw text. To embed a placeholder, call `POST /template-placeholders/prepare` and insert the returned `<tag contenteditable=\"false\" data-type=\"…\" data-identifier=\"…\">…</tag>` element into the HTML at the position where the value should appear.\n"
          }
        },
        "additionalProperties": false
      },
      "TemplatePlaceholder": {
        "type": "object",
        "properties": {
          "type": {
            "type": "string",
            "description": "Placeholder type (system, candidate_column, job_variable, questionnaire_link, scheduling_link)"
          },
          "identifier": {
            "description": "Placeholder identifier (string or integer depending on type)"
          },
          "label": {
            "type": "string",
            "description": "Human-readable label"
          },
          "is_link": {
            "type": "boolean",
            "description": "Whether this placeholder renders as a link"
          },
          "is_job_variable": {
            "type": "boolean",
            "description": "Whether this is a job variable placeholder"
          },
          "job_variable_id": {
            "type": "integer",
            "description": "Job variable ID (for job_variable type)"
          },
          "system_column_title": {
            "type": "string",
            "description": "System column title (for candidate_column type)"
          },
          "qas_profile_question_id": {
            "type": "integer",
            "description": "Profile question ID (for candidate_column type)"
          },
          "form_question_id": {
            "type": "integer",
            "description": "Form question ID (for candidate_column type)"
          },
          "form_name": {
            "type": "string",
            "description": "Form name (for form question placeholders)"
          }
        }
      },
      "TemplatePlaceholderListResponse": {
        "type": "object",
        "required": [
          "placeholders",
          "pagination"
        ],
        "properties": {
          "placeholders": {
            "type": "array",
            "description": "Array of placeholders.",
            "items": {
              "$ref": "#/components/schemas/TemplatePlaceholder"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "PreparePlaceholderRequest": {
        "type": "object",
        "required": [
          "type"
        ],
        "properties": {
          "type": {
            "type": "string",
            "description": "Placeholder type (system, candidate_column, job_variable, questionnaire_link, scheduling_link)"
          },
          "identifier": {
            "type": "string",
            "description": "Placeholder identifier"
          },
          "qas_profile_question_id": {
            "type": "integer",
            "description": "Profile question ID"
          },
          "form_question_id": {
            "type": "integer",
            "description": "Form question ID"
          },
          "system_column_title": {
            "type": "string",
            "description": "System column title"
          },
          "job_variable_id": {
            "type": "integer",
            "description": "Job variable ID"
          }
        },
        "additionalProperties": false
      },
      "NurtureCampaign": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Campaign ID"
          },
          "type": {
            "type": "string",
            "description": "Always \"nurture_campaign\"",
            "example": "nurture_campaign"
          },
          "title": {
            "type": "string",
            "description": "Campaign name"
          },
          "url_backoffice": {
            "type": "string",
            "format": "uri",
            "description": "Absolute backoffice URL to edit this nurture campaign in the 100Hires recruiter app. Use to render deep-links in agent UIs.",
            "example": "https://app.100hires.com/settings/nurture-campaigns/edit?id=42"
          },
          "send_to_all": {
            "type": "boolean",
            "description": "Whether to send to all candidates or only new ones"
          },
          "response_move_to_stage_id": {
            "type": "integer",
            "nullable": true,
            "description": "Stage ID to move candidate when they reply"
          },
          "schedule": {
            "type": "object",
            "description": "Campaign schedule configuration",
            "properties": {
              "formatted": {
                "type": "string",
                "description": "Human-readable schedule description"
              }
            }
          },
          "steps": {
            "type": "array",
            "description": "Ordered list of campaign steps",
            "items": {
              "$ref": "#/components/schemas/NurtureCampaignStep"
            }
          }
        }
      },
      "NurtureCampaignStep": {
        "description": "Campaign step. The shape depends on the step `type`.\n",
        "oneOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepEmail"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepSms"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepVoicemail"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepMoveToNextStage"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepAssignTag"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepAssignTask"
          }
        ],
        "discriminator": {
          "propertyName": "type",
          "mapping": {
            "email": "#/components/schemas/NurtureCampaignStepEmail",
            "sms": "#/components/schemas/NurtureCampaignStepSms",
            "voicemail": "#/components/schemas/NurtureCampaignStepVoicemail",
            "move_to_next_stage": "#/components/schemas/NurtureCampaignStepMoveToNextStage",
            "assign_tag": "#/components/schemas/NurtureCampaignStepAssignTag",
            "assign_task": "#/components/schemas/NurtureCampaignStepAssignTask"
          }
        }
      },
      "NurtureCampaignStepBase": {
        "type": "object",
        "required": [
          "id",
          "type",
          "delay_days",
          "send_condition"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Step ID"
          },
          "type": {
            "type": "string",
            "description": "Step type discriminator."
          },
          "campaign_id": {
            "type": "integer",
            "description": "Parent campaign ID"
          },
          "delay_days": {
            "type": "integer",
            "minimum": 0,
            "description": "Days to wait before executing this step"
          },
          "send_condition": {
            "type": "string",
            "enum": [
              "if_no_reply",
              "if_no_reply_but_opened"
            ],
            "description": "Condition to check before executing step"
          }
        }
      },
      "NurtureCampaignStepEmail": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepBase"
          },
          {
            "type": "object",
            "required": [
              "sender",
              "template_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "email"
                ]
              },
              "sender": {
                "type": "object",
                "description": "Mail sender",
                "properties": {
                  "type": {
                    "type": "string"
                  },
                  "id": {
                    "type": "integer"
                  }
                }
              },
              "template_id": {
                "type": "integer",
                "description": "Email template ID"
              },
              "is_new_thread": {
                "type": "boolean",
                "description": "Send as new email thread"
              },
              "schedule_id": {
                "type": "integer",
                "nullable": true,
                "description": "Sending schedule ID"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepSms": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepBase"
          },
          {
            "type": "object",
            "required": [
              "sender_user_id",
              "template_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "sms"
                ]
              },
              "sender_user_id": {
                "type": "integer",
                "description": "Sender user ID"
              },
              "template_id": {
                "type": "integer",
                "description": "SMS template ID"
              },
              "schedule_id": {
                "type": "integer",
                "nullable": true,
                "description": "Sending schedule ID"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepVoicemail": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepBase"
          },
          {
            "type": "object",
            "description": "Response shape for a voicemail step. Create/update requests use `attachment_uuid`, while responses expand that reference into the full `attachment` payload and do not return `attachment_uuid`.\n",
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "voicemail"
                ]
              },
              "attachment": {
                "$ref": "#/components/schemas/ApiAttachment"
              },
              "schedule_id": {
                "type": "integer",
                "nullable": true,
                "description": "Sending schedule ID"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepMoveToNextStage": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepBase"
          },
          {
            "type": "object",
            "required": [
              "stage_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "move_to_next_stage"
                ]
              },
              "stage_id": {
                "type": "integer",
                "description": "Target pipeline stage ID"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepAssignTag": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepBase"
          },
          {
            "type": "object",
            "required": [
              "tag_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "assign_tag"
                ]
              },
              "tag_id": {
                "type": "integer",
                "description": "Tag ID to assign"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepAssignTask": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepBase"
          },
          {
            "type": "object",
            "required": [
              "task_template_id",
              "assignees"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "assign_task"
                ]
              },
              "task_template_id": {
                "type": "integer",
                "description": "Task template ID"
              },
              "assignees": {
                "type": "array",
                "items": {
                  "type": "integer"
                },
                "description": "Assignee user IDs"
              },
              "due_in_interval": {
                "type": "string",
                "description": "Due date interval, e.g. \"P3D\""
              },
              "priority": {
                "type": "integer",
                "description": "Task priority"
              }
            }
          }
        ]
      },
      "NurtureCampaignListResponse": {
        "type": "object",
        "required": [
          "nurture_campaigns",
          "pagination"
        ],
        "properties": {
          "nurture_campaigns": {
            "type": "array",
            "description": "Array of nurture campaigns.",
            "items": {
              "$ref": "#/components/schemas/NurtureCampaign"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "NurtureCampaignCreateRequest": {
        "type": "object",
        "required": [
          "title",
          "steps"
        ],
        "properties": {
          "company_id": {
            "type": "integer",
            "description": "Target company ID (optional if API key is scoped to one company)"
          },
          "title": {
            "type": "string",
            "description": "Campaign name"
          },
          "workflow_id": {
            "type": "integer",
            "description": "Workflow ID to bind the campaign to"
          },
          "stage_id": {
            "type": "integer",
            "description": "Stage ID that triggers the campaign"
          },
          "delay_time": {
            "type": "integer",
            "description": "Delay time in seconds"
          },
          "relative_days": {
            "type": "integer",
            "description": "Relative days for schedule"
          },
          "relative_time": {
            "type": "integer",
            "description": "Relative time for schedule (seconds from midnight)"
          },
          "timezone": {
            "type": "string",
            "description": "IANA timezone, e.g. \"America/New_York\""
          },
          "send_to_all": {
            "type": "boolean",
            "default": false,
            "description": "Send to all candidates or only new ones"
          },
          "response_move_to_stage_id": {
            "type": "integer",
            "description": "Stage to move candidate to when they reply"
          },
          "steps": {
            "type": "array",
            "description": "Campaign steps (at least one required)",
            "items": {
              "$ref": "#/components/schemas/NurtureCampaignStepInput"
            }
          }
        }
      },
      "NurtureCampaignUpdateRequest": {
        "type": "object",
        "required": [
          "title",
          "steps"
        ],
        "properties": {
          "title": {
            "type": "string",
            "description": "Campaign name"
          },
          "workflow_id": {
            "type": "integer",
            "description": "Workflow ID this campaign is associated with."
          },
          "stage_id": {
            "type": "integer",
            "description": "Pipeline stage ID that triggers the campaign."
          },
          "delay_time": {
            "type": "integer",
            "description": "Delay in minutes before the first step."
          },
          "relative_days": {
            "type": "integer",
            "description": "Number of days offset for scheduling."
          },
          "relative_time": {
            "type": "integer",
            "description": "Time of day for scheduled sends (HH:MM format)."
          },
          "timezone": {
            "type": "string",
            "description": "Timezone for scheduled sends (e.g. America/New_York)."
          },
          "send_to_all": {
            "type": "boolean",
            "description": "Whether to send to all candidates or only new ones."
          },
          "response_move_to_stage_id": {
            "type": "integer",
            "description": "Stage ID to move candidates to when they respond."
          },
          "steps": {
            "type": "array",
            "description": "All steps — mark removed steps with is_deleted=true",
            "items": {
              "$ref": "#/components/schemas/NurtureCampaignStepInput"
            }
          }
        }
      },
      "NurtureCampaignStepInput": {
        "description": "Step input. The required fields depend on the step `type`.\n",
        "oneOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepEmailInput"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepSmsInput"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepVoicemailInput"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepMoveToNextStageInput"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepAssignTagInput"
          },
          {
            "$ref": "#/components/schemas/NurtureCampaignStepAssignTaskInput"
          }
        ],
        "discriminator": {
          "propertyName": "type",
          "mapping": {
            "email": "#/components/schemas/NurtureCampaignStepEmailInput",
            "sms": "#/components/schemas/NurtureCampaignStepSmsInput",
            "voicemail": "#/components/schemas/NurtureCampaignStepVoicemailInput",
            "move_to_next_stage": "#/components/schemas/NurtureCampaignStepMoveToNextStageInput",
            "assign_tag": "#/components/schemas/NurtureCampaignStepAssignTagInput",
            "assign_task": "#/components/schemas/NurtureCampaignStepAssignTaskInput"
          }
        }
      },
      "NurtureCampaignStepInputBase": {
        "type": "object",
        "required": [
          "type",
          "delay_days",
          "send_condition"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Step ID (required for updating existing steps)"
          },
          "type": {
            "type": "string",
            "description": "Step type discriminator."
          },
          "delay_days": {
            "type": "integer",
            "minimum": 0,
            "description": "Days to wait before executing this step"
          },
          "send_condition": {
            "type": "string",
            "description": "Condition for sending this step.",
            "enum": [
              "if_no_reply",
              "if_no_reply_but_opened"
            ]
          },
          "is_deleted": {
            "type": "boolean",
            "description": "Set to true to remove this step during update"
          }
        }
      },
      "NurtureCampaignStepEmailInput": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepInputBase"
          },
          {
            "type": "object",
            "required": [
              "sender",
              "template_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "email"
                ]
              },
              "sender": {
                "type": "object",
                "required": [
                  "type",
                  "id"
                ],
                "properties": {
                  "type": {
                    "type": "string",
                    "description": "Sender type (e.g. \"account\", \"user\")"
                  },
                  "id": {
                    "type": "integer",
                    "description": "Sender ID"
                  }
                }
              },
              "template_id": {
                "type": "integer",
                "description": "Email template ID"
              },
              "is_new_thread": {
                "type": "boolean",
                "description": "Send as new email thread"
              },
              "schedule_id": {
                "type": "integer",
                "description": "Sending schedule ID"
              },
              "is_send_by_carousel": {
                "type": "boolean",
                "description": "Send by carousel rotation"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepSmsInput": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepInputBase"
          },
          {
            "type": "object",
            "required": [
              "sender_user_id",
              "template_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "sms"
                ]
              },
              "sender_user_id": {
                "type": "integer",
                "description": "Sender user ID"
              },
              "template_id": {
                "type": "integer",
                "description": "SMS template ID"
              },
              "schedule_id": {
                "type": "integer",
                "description": "Sending schedule ID"
              },
              "is_send_by_carousel": {
                "type": "boolean",
                "description": "Send by carousel rotation"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepVoicemailInput": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepInputBase"
          },
          {
            "type": "object",
            "required": [
              "attachment_uuid"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "voicemail"
                ]
              },
              "attachment_uuid": {
                "type": "string",
                "format": "uuid",
                "description": "Voicemail audio file UUID. Reuse the `attachment_uuid` from an existing voicemail step, or upload a new audio file through `POST /attachments` with category `voicemail` and use the returned `uuid`."
              },
              "schedule_id": {
                "type": "integer",
                "description": "Sending schedule ID"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepMoveToNextStageInput": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepInputBase"
          },
          {
            "type": "object",
            "required": [
              "stage_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "move_to_next_stage"
                ]
              },
              "stage_id": {
                "type": "integer",
                "description": "Target pipeline stage ID"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepAssignTagInput": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepInputBase"
          },
          {
            "type": "object",
            "required": [
              "tag_id"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "assign_tag"
                ]
              },
              "tag_id": {
                "type": "integer",
                "description": "Tag ID to assign"
              }
            }
          }
        ]
      },
      "NurtureCampaignStepAssignTaskInput": {
        "allOf": [
          {
            "$ref": "#/components/schemas/NurtureCampaignStepInputBase"
          },
          {
            "type": "object",
            "required": [
              "task_template_id",
              "assignees"
            ],
            "properties": {
              "type": {
                "type": "string",
                "enum": [
                  "assign_task"
                ]
              },
              "task_template_id": {
                "type": "integer",
                "description": "Task template ID"
              },
              "assignees": {
                "type": "array",
                "items": {
                  "type": "integer"
                },
                "description": "Assignee user IDs"
              },
              "due_in_interval": {
                "type": "string",
                "description": "Due date interval, e.g. \"P3D\""
              },
              "priority": {
                "type": "integer",
                "description": "Task priority"
              }
            }
          }
        ]
      },
      "QuestionListResponse": {
        "type": "object",
        "required": [
          "questions",
          "pagination"
        ],
        "properties": {
          "questions": {
            "type": "array",
            "description": "Array of questions.",
            "items": {
              "$ref": "#/components/schemas/Question"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "QuestionCreateRequest": {
        "type": "object",
        "required": [
          "text",
          "type"
        ],
        "properties": {
          "company_id": {
            "type": "integer",
            "description": "Target company ID."
          },
          "text": {
            "type": "string",
            "description": "Question text."
          },
          "type": {
            "type": "string",
            "description": "Question type (from GET /questions/types)."
          },
          "options": {
            "type": "array",
            "description": "Answer options (for select/multiselect question types).",
            "items": {
              "type": "string"
            }
          }
        },
        "additionalProperties": false
      },
      "QuestionUpdateRequest": {
        "type": "object",
        "required": [
          "text",
          "type"
        ],
        "properties": {
          "text": {
            "type": "string",
            "description": "Question text."
          },
          "type": {
            "type": "string",
            "description": "Question type (from GET /questions/types)."
          },
          "options": {
            "type": "array",
            "description": "Answer options (for select/multiselect question types).",
            "items": {
              "type": "string"
            }
          }
        },
        "additionalProperties": false
      },
      "QuestionTypesResponse": {
        "type": "object",
        "required": [
          "types"
        ],
        "properties": {
          "types": {
            "type": "array",
            "description": "Array of supported question types.",
            "items": {
              "type": "string"
            }
          }
        }
      },
      "User": {
        "type": "object",
        "required": [
          "id",
          "full_name"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique identifier"
          },
          "full_name": {
            "type": "string",
            "description": "User's full name"
          },
          "email": {
            "type": [
              "string",
              "null"
            ],
            "description": "User's email address"
          },
          "role": {
            "type": [
              "string",
              "null"
            ],
            "description": "User's role in the company (e.g. admin, member)"
          },
          "default_mail_account_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "ID of the user's default mail account. Use this as `from_account_id` when sending emails via `POST /candidates/{id}/messages`. Null if the user has no configured mailbox."
          },
          "created_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          },
          "updated_at": {
            "type": [
              "integer",
              "null"
            ],
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          }
        }
      },
      "UserListResponse": {
        "type": "object",
        "required": [
          "users",
          "pagination"
        ],
        "properties": {
          "users": {
            "type": "array",
            "description": "Array of users.",
            "items": {
              "$ref": "#/components/schemas/User"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "MailAccount": {
        "type": "object",
        "required": [
          "id",
          "email",
          "provider",
          "mailbox_id",
          "is_default",
          "is_configured"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Mail account ID."
          },
          "email": {
            "type": "string",
            "format": "email",
            "description": "Email address."
          },
          "provider": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/MailAccountProvider"
              },
              {
                "type": "null"
              }
            ]
          },
          "mailbox_id": {
            "type": "integer",
            "description": "Internal mailbox ID."
          },
          "is_default": {
            "type": "boolean",
            "description": "Whether this is the default send-from account."
          },
          "is_configured": {
            "type": "boolean",
            "description": "Whether the account is fully configured."
          }
        }
      },
      "MailAccountProvider": {
        "type": "object",
        "required": [
          "name",
          "label"
        ],
        "properties": {
          "name": {
            "type": "string",
            "description": "Provider identifier.",
            "enum": [
              "gmail",
              "outlook"
            ]
          },
          "label": {
            "type": "string",
            "description": "Provider display name."
          }
        }
      },
      "MailAccountListResponse": {
        "type": "object",
        "required": [
          "mail_accounts",
          "pagination"
        ],
        "properties": {
          "mail_accounts": {
            "type": "array",
            "description": "Array of mail accounts.",
            "items": {
              "$ref": "#/components/schemas/MailAccount"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "CompanyMailAccount": {
        "type": "object",
        "required": [
          "id",
          "company_id",
          "user_id",
          "user_email",
          "email",
          "provider",
          "mailbox_id",
          "is_default",
          "is_configured"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Mail account ID."
          },
          "company_id": {
            "type": "integer",
            "description": "Company ID."
          },
          "user_id": {
            "type": "integer",
            "description": "Owner user ID."
          },
          "user_email": {
            "type": "string",
            "format": "email",
            "nullable": true,
            "description": "Owner user email."
          },
          "email": {
            "type": "string",
            "format": "email",
            "description": "Email address."
          },
          "provider": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/MailAccountProvider"
              },
              {
                "type": "null"
              }
            ]
          },
          "mailbox_id": {
            "type": "integer",
            "description": "Internal mailbox ID."
          },
          "is_default": {
            "type": "boolean",
            "description": "Whether this is the user's default send-from account."
          },
          "is_configured": {
            "type": "boolean",
            "description": "Whether the account is fully configured."
          }
        }
      },
      "CompanyMailAccountListResponse": {
        "type": "object",
        "required": [
          "mail_accounts",
          "pagination"
        ],
        "properties": {
          "mail_accounts": {
            "type": "array",
            "description": "Array of mail accounts.",
            "items": {
              "$ref": "#/components/schemas/CompanyMailAccount"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "WorkflowStage": {
        "type": "object",
        "required": [
          "id",
          "name"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Stage ID."
          },
          "name": {
            "type": "string",
            "description": "Stage name."
          },
          "order": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Stage position in the pipeline."
          }
        }
      },
      "Workflow": {
        "type": "object",
        "required": [
          "id",
          "name",
          "stages"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Workflow ID."
          },
          "name": {
            "type": "string",
            "description": "Workflow name."
          },
          "stages": {
            "type": "array",
            "description": "Array of stages in this workflow.",
            "items": {
              "$ref": "#/components/schemas/WorkflowStage"
            }
          }
        }
      },
      "WorkflowListResponse": {
        "type": "object",
        "required": [
          "workflows",
          "pagination"
        ],
        "properties": {
          "workflows": {
            "type": "array",
            "description": "Array of workflows.",
            "items": {
              "$ref": "#/components/schemas/Workflow"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "WorkflowStagesResponse": {
        "type": "object",
        "required": [
          "stages"
        ],
        "properties": {
          "stages": {
            "type": "array",
            "description": "Array of pipeline stages.",
            "items": {
              "$ref": "#/components/schemas/WorkflowStage"
            }
          }
        }
      },
      "StatusesResponse": {
        "type": "object",
        "required": [
          "statuses"
        ],
        "properties": {
          "statuses": {
            "type": "array",
            "description": "Array of job statuses.",
            "items": {
              "type": "string"
            }
          }
        }
      },
      "CategoriesResponse": {
        "type": "object",
        "required": [
          "categories"
        ],
        "properties": {
          "categories": {
            "type": "array",
            "description": "Array of job categories.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "EmploymentTypesResponse": {
        "type": "object",
        "required": [
          "employment_types"
        ],
        "properties": {
          "employment_types": {
            "type": "array",
            "description": "Array of employment types.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "EducationLevelsResponse": {
        "type": "object",
        "required": [
          "education_levels"
        ],
        "properties": {
          "education_levels": {
            "type": "array",
            "description": "Array of education levels.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "ExperienceLevelsResponse": {
        "type": "object",
        "required": [
          "experience_levels"
        ],
        "properties": {
          "experience_levels": {
            "type": "array",
            "description": "Array of experience levels.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "OriginsResponse": {
        "type": "object",
        "required": [
          "origins"
        ],
        "properties": {
          "origins": {
            "type": "array",
            "description": "Array of candidate origins.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "SourcesResponse": {
        "type": "object",
        "required": [
          "sources"
        ],
        "properties": {
          "sources": {
            "type": "array",
            "description": "Array of candidate sources.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "BoardsResponse": {
        "type": "object",
        "required": [
          "boards"
        ],
        "properties": {
          "boards": {
            "type": "array",
            "description": "Array of job boards.",
            "items": {
              "$ref": "#/components/schemas/JobBoardItem"
            }
          }
        }
      },
      "RejectionReasonsResponse": {
        "type": "object",
        "required": [
          "rejection_reasons"
        ],
        "properties": {
          "rejection_reasons": {
            "type": "array",
            "description": "Array of rejection reasons.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "DepartmentsResponse": {
        "type": "object",
        "required": [
          "departments"
        ],
        "properties": {
          "departments": {
            "type": "array",
            "description": "Array of departments.",
            "items": {
              "$ref": "#/components/schemas/IdName"
            }
          }
        }
      },
      "BillingResponse": {
        "type": "object",
        "required": [
          "success",
          "is_pricing_enabled",
          "is_paid"
        ],
        "properties": {
          "success": {
            "type": "boolean",
            "description": "Whether the request succeeded."
          },
          "is_pricing_enabled": {
            "type": "boolean",
            "description": "Whether pricing features are enabled."
          },
          "is_paid": {
            "type": "boolean",
            "description": "Whether the company has an active paid plan."
          }
        }
      },
      "CareerSiteLocation": {
        "type": "object",
        "properties": {
          "city": {
            "type": "string",
            "nullable": true,
            "description": "City."
          },
          "country": {
            "type": "string",
            "nullable": true,
            "description": "Country."
          },
          "state": {
            "type": "string",
            "nullable": true,
            "description": "State or region."
          }
        }
      },
      "CareerSiteJob": {
        "type": "object",
        "required": [
          "id",
          "title",
          "description",
          "location",
          "is_remote",
          "application_url",
          "created_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Job ID."
          },
          "title": {
            "type": "string",
            "description": "Job title."
          },
          "description": {
            "type": "string",
            "description": "HTML content"
          },
          "department": {
            "nullable": true,
            "allOf": [
              {
                "$ref": "#/components/schemas/IdName"
              }
            ]
          },
          "location": {
            "$ref": "#/components/schemas/CareerSiteLocation"
          },
          "employment_type": {
            "nullable": true,
            "allOf": [
              {
                "$ref": "#/components/schemas/IdName"
              }
            ]
          },
          "is_remote": {
            "type": "boolean",
            "description": "Whether this is a remote position."
          },
          "application_url": {
            "type": "string",
            "format": "uri",
            "description": "Public application form URL."
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          }
        }
      },
      "CareerSiteJobDetail": {
        "allOf": [
          {
            "$ref": "#/components/schemas/CareerSiteJob"
          },
          {
            "type": "object",
            "properties": {
              "salary_min": {
                "type": "number",
                "nullable": true
              },
              "salary_max": {
                "type": "number",
                "nullable": true
              },
              "salary_currency": {
                "type": "string",
                "nullable": true,
                "example": "USD"
              },
              "salary_period": {
                "type": "string",
                "nullable": true,
                "example": "annually"
              },
              "education_level": {
                "nullable": true,
                "allOf": [
                  {
                    "$ref": "#/components/schemas/IdName"
                  }
                ]
              },
              "experience_level": {
                "nullable": true,
                "allOf": [
                  {
                    "$ref": "#/components/schemas/IdName"
                  }
                ]
              }
            }
          }
        ]
      },
      "CareerSiteJobListResponse": {
        "type": "object",
        "required": [
          "jobs",
          "pagination"
        ],
        "properties": {
          "jobs": {
            "type": "array",
            "description": "Array of public jobs.",
            "items": {
              "$ref": "#/components/schemas/CareerSiteJob"
            }
          },
          "pagination": {
            "$ref": "#/components/schemas/Pagination"
          }
        }
      },
      "CareerSiteResumeUpload": {
        "type": "object",
        "required": [
          "data",
          "file_name",
          "mime_type"
        ],
        "properties": {
          "data": {
            "type": "string",
            "description": "Base64-encoded file content"
          },
          "file_name": {
            "type": "string",
            "description": "Resume file name.",
            "example": "resume.pdf"
          },
          "mime_type": {
            "type": "string",
            "description": "Resume MIME type.",
            "example": "application/pdf"
          }
        }
      },
      "CareerSiteApplicationRequest": {
        "type": "object",
        "required": [
          "job_id",
          "first_name",
          "last_name",
          "email"
        ],
        "properties": {
          "job_id": {
            "type": "integer",
            "description": "Job ID to apply to."
          },
          "first_name": {
            "type": "string",
            "description": "Applicant first name."
          },
          "last_name": {
            "type": "string",
            "description": "Applicant last name."
          },
          "email": {
            "type": "string",
            "format": "email",
            "description": "Applicant email address."
          },
          "phone": {
            "type": "string",
            "nullable": true,
            "description": "Applicant phone number."
          },
          "resume": {
            "nullable": true,
            "description": "Resume file upload (base64 encoded).",
            "allOf": [
              {
                "$ref": "#/components/schemas/CareerSiteResumeUpload"
              }
            ]
          },
          "linkedin_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Applicant LinkedIn profile URL."
          },
          "source": {
            "type": "string",
            "nullable": true,
            "description": "Application source identifier."
          },
          "answers": {
            "type": "array",
            "nullable": true,
            "description": "Array of form answer objects",
            "items": {
              "type": "object"
            }
          }
        }
      },
      "CareerSiteApplicationResponse": {
        "type": "object",
        "required": [
          "id",
          "job_id",
          "status",
          "created_at"
        ],
        "properties": {
          "id": {
            "type": "integer",
            "description": "Created application ID."
          },
          "job_id": {
            "type": "integer",
            "description": "Job ID."
          },
          "status": {
            "type": "string",
            "description": "Application status.",
            "example": "pending"
          },
          "created_at": {
            "type": "integer",
            "format": "int64",
            "description": "Unix timestamp (seconds)"
          }
        }
      }
    }
  }
}
