{"openapi":"3.0.0","info":{"title":"Sillage Public API","version":"1.0.0","description":"API for accessing workspace signals and lead detection data. Authenticate using an API key provided in the Authorization header as a Bearer token."},"servers":[{"url":"/api","description":"API server"}],"security":[{"ApiKeyAuth":[]}],"paths":{"/v1/workspace/signals":{"get":{"tags":["Signals"],"summary":"List workspace signals","description":"Returns a paginated list of lead detection signals for the authenticated workspace.\n\n---\n\n## What is a signal?\n\nA **signal** is a buying intent event detected by Sillage.\nEach signal is tied to a **lead** in your workspace and carries three top-level objects:\n\n| Field | Description |\n|-------|-------------|\n| `signal` | Metadata - unique ID, when the activity occurred, when Sillage detected it, and the event payload (`signal.data`) |\n| `agent` | The Sillage agent that detected the event (`id`, `name`, `agent_type`) |\n\n---\n\n## Signal fields\n\n| Field | Description |\n|-------|-------------|\n| `signal.id` | Unique document ID of the signal (e.g. `n8ip5inzf8fgwi5ksrrdwy9i`) |\n| `signal.signal_date` | The date the underlying event occurred - e.g. when the post was published or the job change happened. This is the date of the real-world buying signal. |\n| `signal.detection_date` | The date Sillage detected and processed this signal. This date is always ≥ `signal_date`. |\n| `signal.signal_type` | Interaction subtype in snake_case. Use `agent.agent_type` to determine the shape of `signal.data`. |\n\n| Signal type | Description |\n|-------------|-------------|\n| `linkedin_comment` | A lead commented on a competitor's post |\n| `linkedin_reaction` | A lead reacted to a competitor's post |\n| `keyword_detection` | A post matching tracked keywords was detected |\n| `lead_liked_competitor_content` | A lead liked content from a competitor company |\n| `lead_commented_competitor_content` | A lead commented on content from a competitor company |\n| `lead_liked_own_content` | A lead liked content from your own company |\n| `lead_commented_own_content` | A lead commented on content from your own company |\n| `lead_liked_influencer_content` | A lead liked an influencer's post |\n| `lead_commented_influencer_content` | A lead commented on an influencer's post |\n| `new_job` | A lead started a new job |\n| `recently_promoted` | A lead was recently promoted |\n| `deep_search` | A company-level signal detected by AI deep search (e.g. funding, hiring, expansion) |\n| `job_posting` | A job posting matching tracked criteria was published by a target company |\n| `champion_job_change` | A former champion changed jobs, moving to a new company |\n\n> **Example:** A lead comments on a competitor post on Monday (`signal_date = Monday`). Your Sillage campaign runs its nightly scan on Tuesday and picks it up (`detection_date = Tuesday`).\n\n> **Default time window:** when you pass neither `signalStartDate` nor `detectionStartDate`, the endpoint returns only signals from the last **90 days** (by `signal_date`); signals without a `signal_date` are excluded. Pass an explicit `signalStartDate` to reach older signals.\n\n---\n\n## Agent fields\n\n| Field | Description |\n|-------|-------------|\n| `agent.id` | Document ID of the agent that detected the signal |\n| `agent.name` | Human-readable display name of the agent (e.g. `\"Competitors' Activity\"`) |\n| `agent.agent_type` | Agent category. Determines the shape of `signal.data`. |\n\n| Agent type | Agent name | Trigger | Signal data fields |\n|------------|------------|---------|-------------------|\n| `competitor_activity` | `\"Competitors' Activity\"` | A lead commented on or reacted to a **competitor's post** | `interaction` (`type`, `url`, `author`), `post` |\n| `keyword_detection` | `\"Keyword Detection\"` | A post matching your **tracked keywords** was detected | `post`, `keywords_found` |\n| `job_update` | `\"Job Updates\"` | A lead **changed job** or was recently promoted | `previous_position`, `new_position` |\n| `content_engagement` | `\"Content Engagement\"` | A lead engaged with tracked content: your own posts, or — from a competitor agent's lead discovery — a tracked competitor's employees' posts | `interaction` (`type`, `url`, `author`), `post` |\n| `influencer_engagement` | `\"Influencer Engagement\"` | A lead engaged with an **influencer's post** | `interaction` (`type`, `url`, `author`), `post` |\n| `deep_search` | `\"Deep Search\"` | A **company-level signal** was detected by AI research (e.g., funding round, hiring wave, expansion, etc.) | `title`, `tag`, `date`, `sources` |\n| `job_posting` | `\"Job Posting\"` | A **job posting** matching your tracked criteria was published by a target company | `posting` (`title`, `job_url`, `location`), `job_title` |\n| `champion_tracking` | `\"Champion Tracking\"` | A former champion **moved to a new company** (tracked via enrichment) | `previous_position`, `new_position` |\n\n> **Note:** `competitor_activity` and `content_engagement` are both labels a single **competitor** agent's lead-discovery results can carry, one per direction of engagement — the agent itself keeps type `competitor`. `content_engagement` also remains the reported type of content-engagement agents created before this pairing existed.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","description":"Page number (starts at 1). Defaults to 1.","schema":{"type":"integer","minimum":1}},{"name":"pageSize","in":"query","description":"Number of items per page. Defaults to 25. Maximum: 100.","schema":{"type":"integer","minimum":1,"maximum":100}},{"name":"signalStartDate","in":"query","description":"Filter signals whose activity date (`signal_date`) is on or after this date (ISO 8601). When neither `signalStartDate` nor `detectionStartDate` is provided, results default to the last 90 days of `signal_date`; signals without a `signal_date` are excluded from that default window.","schema":{"type":"string","format":"date-time"}},{"name":"signalEndDate","in":"query","description":"Filter signals whose activity date (`signal_date`) is on or before this date (ISO 8601)","schema":{"type":"string","format":"date-time"}},{"name":"detectionStartDate","in":"query","description":"Filter signals detected by Sillage (`detection_date`) on or after this date (ISO 8601)","schema":{"type":"string","format":"date-time"}},{"name":"detectionEndDate","in":"query","description":"Filter signals detected by Sillage (`detection_date`) on or before this date (ISO 8601)","schema":{"type":"string","format":"date-time"}},{"name":"agentType","in":"query","description":"Filter by agent type. Comma-separated or repeated.","style":"form","explode":false,"schema":{"type":"array","items":{"type":"string","enum":["competitor_activity","keyword_detection","job_update","content_engagement","champion_tracking","influencer_engagement","company_interaction","profile_interaction"]}}},{"name":"agentId","in":"query","description":"Filter signals by a specific agent document ID (nanoid format).","schema":{"type":"string"}},{"name":"sort","in":"query","description":"Sort order. Comma-separated list of fields, prefix with `-` for descending.\nSupported fields: `signalDate`, `detectionDate`, `companyName`, `leadLastName`, `employeeCount`.\n\nSingle field: `-signalDate`, `-companyName`, `-detectionDate`\n\nMultiple fields: `-signalDate,companyName`","schema":{"type":"string"}}],"responses":{"200":{"description":"Paginated list of signals","headers":{"X-Request-Id":{"description":"Unique identifier for this request, useful for debugging and support","schema":{"type":"string","format":"uuid","example":"5d43a1a6-1b86-4a99-97b9-a3c955454bc2"}},"X-Response-Time":{"description":"Total server processing time for this request","schema":{"type":"string","example":"35ms"}},"Cache-Control":{"description":"Caching directives for this response","schema":{"type":"string","example":"private, no-store"}},"X-RateLimit-Limit":{"description":"Maximum number of requests allowed in the current window","schema":{"type":"integer","example":60}},"X-RateLimit-Remaining":{"description":"Number of requests remaining in the current window","schema":{"type":"integer","example":58}},"X-RateLimit-Reset":{"description":"Unix timestamp (ms) when the rate limit window resets","schema":{"type":"integer","example":1771513314613}},"X-Total-Count":{"description":"Total number of signals matching the query (across all pages)","schema":{"type":"integer","example":720}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":10}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":72}}},"content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"oneOf":[{"title":"competitor_activity","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/CompetitorActivityData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["competitor_activity"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"keyword_detection","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/KeywordDetectionData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["keyword_detection"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"job_update","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/JobUpdateData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["job_update"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"content_engagement","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/ContentEngagementData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["content_engagement"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"champion_tracking","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"type":"object","required":["change_type","previous_position","new_position"],"properties":{"change_type":{"type":"string","nullable":true},"previous_position":{"type":"object","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true}}},"new_position":{"type":"object","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"start_date":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true}}}}}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["champion_tracking"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"influencer_engagement","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/InfluencerEngagementData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["influencer_engagement"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"deep_search","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/DeepSearchData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["deep_search"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"job_posting","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/JobPostingData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["job_posting"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}},{"title":"job_posting_keyword_detection","type":"object","required":["signal","agent","lead"],"properties":{"signal":{"type":"object","required":["id","signal_date","detection_date","signal_type","data"],"properties":{"id":{"type":"string","description":"Document ID of the signal"},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when the LinkedIn activity occurred (e.g. when the post was published or the job change happened)"},"detection_date":{"type":"string","format":"date-time","nullable":true,"description":"Date when Sillage detected this signal"},"signal_type":{"type":"string","nullable":true,"enum":["linkedin_comment","linkedin_reaction","keyword_detection","lead_liked_competitor_content","lead_commented_competitor_content","lead_liked_own_content","lead_commented_own_content","lead_liked_influencer_content","lead_commented_influencer_content","recently_promoted","new_job","deep_search","job_posting","job_posting_insight","job_posting_hiring_manager","job_posting_keyword_detection",null],"description":"Signal subtype (snake_case). Use `agent.agent_type` to determine the shape of `signal.data`."},"data":{"$ref":"#/components/schemas/JobPostingKeywordDetectionData"}}},"agent":{"type":"object","required":["id","name","agent_type"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the agent that detected this signal"},"name":{"type":"string","description":"Display name of the agent (e.g. \"Competitors' Activity\", \"Keyword Detection\")"},"agent_type":{"type":"string","enum":["job_posting_keyword_detection"]}}},"lead":{"type":"object","required":["id","first_name","last_name","linkedin_url","avatar_url","email","phone_number","position","linkedin_handle","linkedin_headline","linkedin_about","location","current_company"],"properties":{"id":{"type":"string","nullable":true,"description":"Document ID of the workspace lead"},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"Email address from the workspace lead record, with fallback to the profile email (null if neither is set)"},"phone_number":{"type":"string","nullable":true,"description":"Phone number from the workspace lead record (null if not set)"},"position":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"salesforce":{"type":"object","nullable":true,"description":"Salesforce IDs when a CRM match exists. Only present if the workspace has a Salesforce credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"Salesforce Contact ID"},"account_id":{"type":"string","nullable":true,"description":"Salesforce Account ID"}}},"hubspot":{"type":"object","nullable":true,"description":"HubSpot IDs when a CRM match exists. Only present if the workspace has a HubSpot credential installed.","properties":{"contact_id":{"type":"string","nullable":true,"description":"HubSpot Contact ID"},"account_id":{"type":"string","nullable":true,"description":"HubSpot Company ID"}}},"current_company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"website_url":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"number_of_employees":{"type":"integer","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true},"industries":{"type":"string","nullable":true},"founded_year":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request. Omitted when it was not resolved for this response."}}}}}}}]}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","pageSize","pageCount","total"],"properties":{"page":{"type":"integer","description":"Current page"},"pageSize":{"type":"integer","description":"Items per page"},"pageCount":{"type":"integer","description":"Total number of pages"},"total":{"type":"integer","description":"Total number of signals"}}}}}}},"examples":{"competitor_activity":{"summary":"Competitor activity signal","value":{"data":[{"signal":{"id":"n8ip5inzf8fgwi5ksrrdwy9i","signal_date":"2025-09-09T08:15:00.000Z","detection_date":"2025-09-09T10:30:00.000Z","signal_type":"linkedin_comment","data":{"interaction":{"type":"comment","url":"https://www.linkedin.com/feed/update/urn:li:activity:0000000000000000001/#comment-001","author":{"full_name":"Arthur Coudouy","first_name":"Arthur","last_name":"Coudouy","linkedin_url":"https://www.linkedin.com/in/arthurcoudouy","company_name":"Sillage","role":"Co-founder & CTO","comment_text":"Congrats Sarah! Well deserved, looking forward to seeing what's next."}},"post":{"url":"https://www.linkedin.com/feed/update/urn:li:activity:0000000000000000001/","extract":"We just closed our Series A. Excited to keep building the future of B2B sales with an incredible team.","author":{"full_name":"Jane Doe","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","company_name":"Acme Corp","role":"Head of Sales"}}}},"agent":{"id":"abc123","name":"Competitors' Activity","agent_type":"competitor_activity"},"lead":{"id":"a1b2c3d4e5f6g7h8i9j0klm","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","avatar_url":null,"email":null,"phone_number":null,"position":"Head of Sales","linkedin_handle":"jane-doe-example","linkedin_headline":"Head of Sales @ Acme Corp | B2B Sales","linkedin_about":null,"location":"Paris, Île-de-France, France","salesforce":{"contact_id":"003xx000004TMMaBC","account_id":"001xx000008ABCdEF"},"hubspot":{"contact_id":"501","account_id":"9872345"},"current_company":{"name":"Acme Corp","website_url":"https://www.acme-example.com","linkedin_url":"https://www.linkedin.com/company/acme-example","number_of_employees":250,"linkedin_handle":"acme-example","activity_summary":null,"logo_url":null,"industries":"Software Development","founded_year":2015,"employee_range":"201-500"}}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}},"keyword_detection":{"summary":"Keyword detection signal","value":{"data":[{"signal":{"id":"n8dz5inzf8fgwiksrrdwy9i","signal_date":"2025-09-09T08:15:00.000Z","detection_date":"2025-09-09T11:00:00.000Z","signal_type":"keyword_detection","data":{"post":{"url":"https://www.linkedin.com/posts/jane-doe-example-buyingsignals-activity-0000000000000000002","extract":"We're evaluating new sales intelligence tools to help our team prioritize outreach. Buying signals and AI-powered prospecting are top of mind this quarter.","author":{"full_name":"Jane Doe","headline":"VP Sales @ Acme Inc | B2B Revenue Growth","linkedin_url":"https://www.linkedin.com/in/jane-doe-example"}},"keywords_found":["buying signals","sales intelligence"]}},"agent":{"id":"def456","name":"Keyword Detection","agent_type":"keyword_detection"},"lead":{"id":"a1b2c3d4e5f6g7h8i9j0klm","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","avatar_url":null,"email":null,"phone_number":null,"position":"VP Sales","linkedin_handle":"jane-doe-example","linkedin_headline":"VP Sales @ Acme Inc | Former Head of Sales @ Acme Corp","linkedin_about":null,"location":"Paris, Île-de-France, France","current_company":{"name":"Acme Inc","website_url":"https://www.acme-inc-example.com","linkedin_url":"https://www.linkedin.com/company/acme-inc-example","number_of_employees":null,"linkedin_handle":"acme-inc-example","activity_summary":null,"logo_url":null,"industries":"SaaS","founded_year":null,"employee_range":"11-50"}}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}},"job_update":{"summary":"Job update signal","value":{"data":[{"signal":{"id":"n8gh5inzf8fgwiksrrdwy9i","signal_date":"2025-09-01T00:00:00.000Z","detection_date":"2025-09-09T14:00:00.000Z","signal_type":"new_job","data":{"previous_position":{"role":"Head of Sales","company_name":"Acme Corp"},"new_position":{"role":"VP Sales","company_name":"Appleseed Inc","start_date":"2025-09-01T00:00:00.000Z"}}},"agent":{"id":"ghi789","name":"Job Updates","agent_type":"job_update"},"lead":{"id":"a1b2c3d4e5f6g7h8i9j0klm","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","avatar_url":null,"email":null,"phone_number":null,"position":"VP Sales","linkedin_handle":"jane-doe-example","linkedin_headline":"VP Sales @ Appleseed Inc | Former Head of Sales @ Acme Corp","linkedin_about":null,"location":"Paris, Île-de-France, France","hubspot":{"contact_id":"60123","account_id":"9001234"},"current_company":{"name":"Appleseed Inc","website_url":"https://www.appleseed-example.com","linkedin_url":"https://www.linkedin.com/company/appleseed-inc-example","number_of_employees":45,"linkedin_handle":"appleseed-inc-example","activity_summary":null,"logo_url":null,"industries":"Software Development","founded_year":2022,"employee_range":"11-50"}}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}},"content_engagement":{"summary":"Content engagement signal","value":{"data":[{"signal":{"id":"n8jk5inzf8fgwiksrrdwy9i","signal_date":"2025-09-09T08:15:00.000Z","detection_date":"2025-09-09T12:00:00.000Z","signal_type":"lead_liked_competitor_content","data":{"interaction":{"type":"reaction","url":null,"author":{"full_name":"Jane Doe","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","company_name":"Acme Corp","role":"Head of Sales","comment_text":null}},"post":{"url":"https://www.linkedin.com/feed/update/urn:li:activity:0000000000000000003/","extract":"Sillage detects buying signals from LinkedIn in real time - so your sales team reaches out at exactly the right moment.","author":{"full_name":"Arthur Coudouy","first_name":"Arthur","last_name":"Coudouy","linkedin_url":"https://www.linkedin.com/in/arthurcoudouy","company_name":"Sillage","role":"Co-founder & CTO"}}}},"agent":{"id":"jkl012","name":"Content Engagement","agent_type":"content_engagement"},"lead":{"id":"a1b2c3d4e5f6g7h8i9j0klm","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","avatar_url":null,"email":null,"phone_number":null,"position":"Head of Sales","linkedin_handle":"jane-doe-example","linkedin_headline":"Head of Sales @ Acme Corp | B2B Sales","linkedin_about":null,"location":null,"current_company":null}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}},"champion_tracking":{"summary":"Champion tracking signal","value":{"data":[{"signal":{"id":"n8mn5inzf8fgwiksrrdwy9i","signal_date":"2025-09-01T00:00:00.000Z","detection_date":"2025-09-09T15:30:00.000Z","signal_type":"new_job","data":{"change_type":"company_change","previous_position":{"role":"Head of Sales","company_name":"Acme Corp","linkedin_url":"https://www.linkedin.com/company/acme-example"},"new_position":{"role":"VP Sales","company_name":"Appleseed Inc","start_date":"2025-09-01T00:00:00.000Z","linkedin_url":"https://www.linkedin.com/company/acme-inc-example"}}},"agent":{"id":"mno345","name":"Champion Tracking","agent_type":"champion_tracking"},"lead":{"first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","avatar_url":null,"email":null,"phone_number":null,"position":"VP Sales","linkedin_handle":"jane-doe-example","linkedin_headline":"VP Sales @ Appleseed Inc | Former Head of Sales @ Acme Corp","linkedin_about":null,"location":"Paris, Île-de-France, France","current_company":{"name":"Appleseed Inc","website_url":"https://www.appleseed-inc-example.com","linkedin_url":"https://www.linkedin.com/company/appleseed-inc-example","number_of_employees":45,"linkedin_handle":"appleseed-inc-example","activity_summary":null,"logo_url":null,"industries":"Software Development","founded_year":2022,"employee_range":"11-50"}}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}},"deep_search":{"summary":"Deep search signal","value":{"data":[{"signal":{"id":"ds1abc2def3ghi4jkl5mno","signal_date":"2025-09-01T00:00:00.000Z","detection_date":"2025-09-09T14:00:00.000Z","signal_type":"deep_search","data":{"title":"Series B Funding Round","tag":"funding","date":"2025-09-01","sources":[{"url":"https://example.com/news/series-b","excerpts":["Company raised $50M in Series B funding"]}]}},"agent":{"id":"agent-ds-001","name":"Deep Search","agent_type":"deep_search"},"lead":{"id":"a1b2c3d4e5f6g7h8i9j0klm","first_name":null,"last_name":null,"linkedin_url":null,"avatar_url":null,"email":null,"phone_number":null,"position":null,"linkedin_handle":null,"linkedin_headline":null,"linkedin_about":null,"location":null,"current_company":{"name":"Target Corp","website_url":"https://www.target-corp-example.com","linkedin_url":"https://www.linkedin.com/company/target-corp-example","number_of_employees":500,"linkedin_handle":"target-corp-example","activity_summary":null,"logo_url":null,"industries":"Software Development","founded_year":2018,"employee_range":"201-500"}}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}},"job_posting":{"summary":"Job posting signal","value":{"data":[{"signal":{"id":"jp1abc2def3ghi4jkl5mno","signal_date":"2025-09-05T00:00:00.000Z","detection_date":"2025-09-09T16:00:00.000Z","signal_type":"job_posting","data":{"posting":{"title":"Senior Sales Engineer","company_name":"Acme Corp","job_url":"https://www.linkedin.com/jobs/view/123456","location":"Paris, France","description":"We are looking for a Senior Sales Engineer...","published_at":"2025-09-05T00:00:00.000Z"},"job_title":"Sales Engineer"}},"agent":{"id":"agent-jp-001","name":"Job Posting","agent_type":"job_posting"},"lead":{"id":"a1b2c3d4e5f6g7h8i9j0klm","first_name":null,"last_name":null,"linkedin_url":null,"avatar_url":null,"email":null,"phone_number":null,"position":null,"linkedin_handle":null,"linkedin_headline":null,"linkedin_about":null,"location":null,"current_company":{"name":"Acme Corp","website_url":"https://www.acme-corp-example.com","linkedin_url":"https://www.linkedin.com/company/acme-corp-example","number_of_employees":250,"linkedin_handle":"acme-corp-example","activity_summary":null,"logo_url":null,"industries":"Software Development","founded_year":2015,"employee_range":"201-500"}}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}},"influencer_engagement":{"summary":"Influencer engagement signal","value":{"data":[{"signal":{"id":"n8pq5inzf8fgwiksrrdwy9i","signal_date":"2025-09-09T08:15:00.000Z","detection_date":"2025-09-09T13:45:00.000Z","signal_type":"lead_commented_influencer_content","data":{"interaction":{"type":"comment","url":"https://www.linkedin.com/posts/arnaud-weiss-example-activity-0000000000000000004#comment-002","author":{"full_name":"Jane Doe","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","company_name":"Acme Corp","role":"Head of Sales","comment_text":"Totally agree - we've been testing this approach internally and the results are impressive."}},"post":{"url":"https://www.linkedin.com/posts/arnaud-weiss-example-activity-0000000000000000004","extract":"AI is not replacing sales reps - it's giving them superpowers. Here's how signal-driven outreach is changing the game.","author":{"full_name":"Arnaud Weiss","first_name":"Arnaud","last_name":"Weiss","linkedin_url":"https://www.linkedin.com/in/arnaud-weiss-60b6758a/","company_name":"Sillage","role":"Co-founder & CEO"}}}},"agent":{"id":"pqr678","name":"Influencer Engagement","agent_type":"influencer_engagement"},"lead":{"id":"a1b2c3d4e5f6g7h8i9j0klm","first_name":"Jane","last_name":"Doe","linkedin_url":"https://www.linkedin.com/in/jane-doe-example","avatar_url":null,"email":null,"phone_number":null,"position":"Head of Sales","linkedin_handle":"jane-doe-example","linkedin_headline":"Head of Sales @ Acme Corp | B2B Sales","linkedin_about":null,"location":null,"current_company":null}}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":1,"total":1}}}}}}}},"400":{"description":"Bad request - Invalid query parameters","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":400},"name":{"type":"string","example":"BadRequestError"},"message":{"type":"string","example":"Invalid query parameters"}}}}}}}},"401":{"description":"Unauthorized - Invalid or missing API key","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":401},"name":{"type":"string","example":"UnauthorizedError"},"message":{"type":"string","example":"Invalid or expired API key"}}}}}}}},"429":{"description":"Too Many Requests - Rate limit exceeded","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-RateLimit-Limit":{"description":"Maximum number of requests allowed in the current window","schema":{"type":"integer","example":60}},"X-RateLimit-Remaining":{"description":"Always 0 when rate limit is exceeded","schema":{"type":"integer","example":0}},"X-RateLimit-Reset":{"description":"Unix timestamp (ms) when the rate limit window resets","schema":{"type":"integer","example":1771513314613}},"Retry-After":{"description":"Number of seconds to wait before retrying","schema":{"type":"integer","example":47}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":429},"name":{"type":"string","example":"TooManyRequestsError"},"message":{"type":"string","example":"Rate limit exceeded. Try again in 47 seconds."}}}}}}}},"500":{"description":"Internal server error","headers":{"X-Request-Id":{"description":"Unique identifier for this request - include this when reporting errors","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":500},"name":{"type":"string","example":"InternalServerError"},"message":{"type":"string","example":"An error occurred while fetching signals"}}}}}}}}}}},"/v1/workspace/leads":{"get":{"tags":["Leads"],"summary":"List workspace leads","description":"Returns a paginated list of leads for the authenticated workspace.\n\n---\n\n## What is a lead?\n\nA **lead** is a person detected by Sillage as a potential sales opportunity.\nEach lead has a **status** (e.g. `pending`, `contacted_email`, `meeting_booked`).\n\n## Status groups (query parameter)\n\nThe `status` query parameter filters leads by group. Each group includes one or more individual statuses:\n\n| Group | Included statuses |\n|-------|-------------------|\n| `pending` | `pending` |\n| `contacted` | `contacted_email`, `contacted_phone`, `contacted_linkedin` |\n| `interested` | `need_follow_up`, `already_in_touch`, `meeting_booked`, `customer` |\n| `all` | All active statuses |\n\n## Individual status values (response field)\n\n| Status | Description |\n|--------|-------------|\n| `pending` | New lead, not yet contacted |\n| `contacted_email` | Contacted via email |\n| `contacted_phone` | Contacted via phone |\n| `contacted_linkedin` | Contacted via LinkedIn |\n| `meeting_booked` | Meeting has been booked |\n| `need_follow_up` | Requires follow-up |\n| `already_in_touch` | Already in contact |\n| `customer` | Converted to customer |\n| `declined` | Lead declined |\n| `disqualified` | Lead disqualified |\n","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","description":"Page number (starts at 1). Defaults to 1.","schema":{"type":"integer","minimum":1}},{"name":"pageSize","in":"query","description":"Number of items per page. Defaults to 25. Maximum: 100.","schema":{"type":"integer","minimum":1,"maximum":100}},{"name":"status","in":"query","description":"Filter leads by status group. See the **Status groups** table above for details.","schema":{"type":"string","enum":["pending","contacted","interested","all"],"default":"pending"}},{"name":"sortBy","in":"query","description":"Field to sort by. Defaults to `firstSeenAt`.","schema":{"type":"string","enum":["firstSeenAt","lastSignalAt"],"default":"firstSeenAt"}},{"name":"sortOrder","in":"query","description":"Sort direction. Defaults to `desc`.","schema":{"type":"string","enum":["asc","desc"],"default":"desc"}},{"name":"search","in":"query","description":"Free-text search across name, email, company, and LinkedIn URL (of the lead). Max 200 characters.","schema":{"type":"string","maxLength":200}},{"name":"industries","in":"query","description":"Filter by industry names from company profiles. Comma-separated. Use GET /leads without this filter to discover available values.","style":"form","explode":false,"schema":{"type":"string"}},{"name":"ownerIds","in":"query","description":"Filter by owner document IDs (the `owner.id` field in the lead response). Comma-separated. Use `unassigned` to filter leads without an owner.","style":"form","explode":false,"schema":{"type":"string"}},{"name":"countries","in":"query","description":"Filter by country names. Comma-separated.","style":"form","explode":false,"schema":{"type":"string"}}],"responses":{"200":{"description":"Paginated list of leads","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"35ms"}},"X-RateLimit-Limit":{"description":"Maximum requests allowed in the current window","schema":{"type":"integer","example":60}},"X-RateLimit-Remaining":{"description":"Requests remaining in the current window","schema":{"type":"integer","example":58}},"X-Total-Count":{"description":"Total number of leads matching the query","schema":{"type":"integer","example":87}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":4}}},"content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id","firstSeenAt","lastSignalAt","isExpired","email","phoneNumber","firstName","lastName","linkedinUrl","linkedinHandle","position","company","owner","signals"],"properties":{"id":{"type":"string","description":"Unique identifier of the lead"},"status":{"type":"string","nullable":true,"description":"Lead status (snake_case). Always present but may be `null` if the internal status has no known mapping."},"firstSeenAt":{"type":"string","format":"date-time","nullable":true,"description":"When the lead was first detected"},"lastSignalAt":{"type":"string","format":"date-time","nullable":true,"description":"When the last signal was detected for this lead"},"isExpired":{"type":"boolean","description":"Whether the lead has expired"},"email":{"type":"string","nullable":true,"description":"Best available email: enriched email > lead email > profile email"},"phoneNumber":{"type":"string","nullable":true,"description":"Best available phone: enriched phone > lead phone"},"firstName":{"type":"string","nullable":true},"lastName":{"type":"string","nullable":true},"linkedinUrl":{"type":"string","nullable":true},"linkedinHandle":{"type":"string","nullable":true},"position":{"type":"string","nullable":true},"company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true},"linkedinUrl":{"type":"string","nullable":true},"numberOfEmployees":{"type":"integer","nullable":true}}},"owner":{"type":"object","nullable":true,"properties":{"id":{"type":"string"},"email":{"type":"string"},"firstName":{"type":"string","nullable":true},"lastName":{"type":"string","nullable":true}}},"signals":{"type":"array","description":"List of detections (signals) associated with this lead","items":{"type":"object","required":["id","signalType","detectedAt","signalDate","agent","data","agentType"],"properties":{"id":{"type":"string","description":"Unique identifier of the signal"},"signalType":{"type":"string","description":"Type of signal (snake_case)"},"detectedAt":{"type":"string","format":"date-time","nullable":true,"description":"When the signal was detected"},"signalDate":{"type":"string","format":"date-time","nullable":true,"description":"When the signal event occurred"},"agent":{"type":"object","nullable":true,"properties":{"id":{"type":"string","nullable":true},"name":{"type":"string","nullable":true}}},"data":{"nullable":true,"description":"Agent-type-specific signal payload. Shape depends on `agentType`. See the schema definitions below for each agent type.","oneOf":[{"$ref":"#/components/schemas/CompetitorActivityData"},{"$ref":"#/components/schemas/KeywordDetectionData"},{"$ref":"#/components/schemas/JobUpdateData"},{"$ref":"#/components/schemas/ContentEngagementData"},{"$ref":"#/components/schemas/InfluencerEngagementData"},{"$ref":"#/components/schemas/DeepSearchData"},{"$ref":"#/components/schemas/JobPostingData"},{"$ref":"#/components/schemas/JobPostingKeywordDetectionData"}]},"agentType":{"type":"string","nullable":true,"description":"Agent category that detected this signal. Determines the shape of `data`.","enum":["competitor_activity","keyword_detection","job_update","content_engagement","influencer_engagement","deep_search","job_posting","job_posting_keyword_detection","company_interaction","profile_interaction"]}}}}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","pageSize","pageCount","total"],"properties":{"page":{"type":"integer"},"pageSize":{"type":"integer"},"pageCount":{"type":"integer"},"total":{"type":"integer"}}}}}}},"examples":{"default":{"summary":"Paginated leads response","value":{"data":[{"id":"abc123def456ghi789jkl0mn","status":"pending","firstSeenAt":"2026-03-01T10:00:00.000Z","lastSignalAt":"2026-03-15T14:30:00.000Z","isExpired":false,"email":"john@example.com","phoneNumber":"+33612345678","firstName":"John","lastName":"Snow","linkedinUrl":"https://linkedin.com/in/john-snow","linkedinHandle":"john-snow","position":"VP Sales","company":{"name":"Example Inc","domain":"example.com","linkedinUrl":"https://linkedin.com/company/example","numberOfEmployees":250},"owner":{"id":"usr123abc456def789ghi0jk","email":"john@appleseed.com","firstName":"John","lastName":"Appleseed"},"signals":[{"id":"det123abc456def789ghi0jk","signalType":"new_job","detectedAt":"2026-03-01T10:00:00.000Z","signalDate":"2026-02-28T00:00:00.000Z","agent":{"id":"agent123","name":"Job Updates"},"data":{"previous_company":"Acme Corp","previous_position":"Sales Director","new_company":"Example Inc","new_position":"VP Sales"},"agentType":"job_update"},{"id":"det456abc789def012ghi3jk","signalType":"keyword_detection","detectedAt":"2026-03-15T14:30:00.000Z","signalDate":"2026-03-15T14:00:00.000Z","agent":{"id":"agent456","name":"Keyword Tracker"},"data":{"post":{"url":"https://linkedin.com/posts/example","extract":"Looking for new sales tools..."},"keywords_found":["sales tools"]},"agentType":"keyword_detection"}]}],"meta":{"pagination":{"page":1,"pageSize":25,"pageCount":4,"total":87}}}}}}}},"400":{"description":"Bad request - Invalid query parameters","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":400},"name":{"type":"string","example":"BadRequestError"},"message":{"type":"string","example":"Invalid query parameters"}}}}}}}},"401":{"description":"Unauthorized - Invalid or missing API key","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":401},"name":{"type":"string","example":"UnauthorizedError"},"message":{"type":"string","example":"Invalid or expired API key"}}}}}}}},"429":{"description":"Too Many Requests - Rate limit exceeded","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-RateLimit-Limit":{"description":"Maximum number of requests allowed in the current window","schema":{"type":"integer","example":60}},"X-RateLimit-Remaining":{"description":"Always 0 when rate limit is exceeded","schema":{"type":"integer","example":0}},"X-RateLimit-Reset":{"description":"Unix timestamp (ms) when the rate limit window resets","schema":{"type":"integer","example":1771513314613}},"Retry-After":{"description":"Number of seconds to wait before retrying","schema":{"type":"integer","example":47}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":429},"name":{"type":"string","example":"TooManyRequestsError"},"message":{"type":"string","example":"Rate limit exceeded. Try again in 47 seconds."}}}}}}}},"500":{"description":"Internal server error","headers":{"X-Request-Id":{"description":"Unique identifier for this request - include this when reporting errors","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"object","properties":{"status":{"type":"integer","example":500},"name":{"type":"string","example":"InternalServerError"},"message":{"type":"string","example":"An error occurred while fetching leads"}}}}}}}}}}},"/v1/workspace/leads/{id}":{"patch":{"tags":["Leads"],"summary":"Update a workspace lead","description":"Updates a single field on a workspace lead.\n\n---\n\n## Status values\n\n| Status | Description |\n|--------|-------------|\n| `pending` | Default status for new leads |\n| `contacted_email` | Contacted via email |\n| `contacted_phone` | Contacted via phone |\n| `contacted_linkedin` | Contacted via LinkedIn |\n| `meeting_booked` | Meeting has been booked |\n| `need_follow_up` | Requires follow-up |\n| `already_in_touch` | Already in contact |\n| `customer` | Converted to customer |\n| `declined` | Lead declined |\n| `disqualified` | Lead disqualified |\n| `company_not_icp` | Company does not match ICP |\n| `job_title_not_icp` | Job title does not match ICP |\n\n---\n\n## Owner\n\nSet `owner` to a workspace member's email to assign ownership.\n\nSet `owner=null` to unassign the current owner.\n","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"Unique identifier of the lead to update.","schema":{"type":"string"}},{"name":"status","in":"query","description":"New lead status.","schema":{"type":"string","enum":["pending","contacted_email","contacted_phone","contacted_linkedin","meeting_booked","need_follow_up","already_in_touch","customer","declined","disqualified","company_not_icp","job_title_not_icp"]}},{"name":"owner","in":"query","description":"Email of a workspace member to assign as owner. Send `null` to unassign.","schema":{"type":"string"}}],"responses":{"200":{"description":"Updated lead","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"45ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","status","firstSeenAt","lastSignalAt","isExpired","email","phoneNumber","firstName","lastName","linkedinUrl","linkedinHandle","position","company","owner","signals"],"properties":{"id":{"type":"string"},"status":{"type":"string","nullable":true},"firstSeenAt":{"type":"string","format":"date-time","nullable":true},"lastSignalAt":{"type":"string","format":"date-time","nullable":true},"isExpired":{"type":"boolean"},"email":{"type":"string","nullable":true},"phoneNumber":{"type":"string","nullable":true},"firstName":{"type":"string","nullable":true},"lastName":{"type":"string","nullable":true},"linkedinUrl":{"type":"string","nullable":true},"linkedinHandle":{"type":"string","nullable":true},"position":{"type":"string","nullable":true},"company":{"type":"object","nullable":true,"properties":{"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true},"linkedinUrl":{"type":"string","nullable":true},"numberOfEmployees":{"type":"integer","nullable":true}}},"owner":{"type":"object","nullable":true,"properties":{"id":{"type":"string"},"email":{"type":"string"},"firstName":{"type":"string","nullable":true},"lastName":{"type":"string","nullable":true}}},"signals":{"type":"array","description":"List of detections (signals) associated with this lead","items":{"type":"object","required":["id","signalType","detectedAt","signalDate","agent","data","agentType"],"properties":{"id":{"type":"string","description":"Unique identifier of the signal"},"signalType":{"type":"string","description":"Type of signal (snake_case)"},"detectedAt":{"type":"string","format":"date-time","nullable":true,"description":"When the signal was detected"},"signalDate":{"type":"string","format":"date-time","nullable":true,"description":"When the signal event occurred"},"agent":{"type":"object","nullable":true,"properties":{"id":{"type":"string","nullable":true},"name":{"type":"string","nullable":true}}},"data":{"nullable":true,"description":"Agent-type-specific signal payload. Shape depends on `agentType`. Same format as `signal.data` in the GET /v1/workspace/signals endpoint."},"agentType":{"type":"string","nullable":true,"description":"Agent category that detected this signal. Determines the shape of `data`.","enum":["competitor_activity","keyword_detection","job_update","content_engagement","influencer_engagement","deep_search","job_posting","job_posting_keyword_detection","company_interaction","profile_interaction"]}}}}}}}},"examples":{"default":{"summary":"Updated lead response","value":{"data":{"id":"abc123def456ghi789jkl0mn","status":"contacted_email","firstSeenAt":"2026-03-01T10:00:00.000Z","lastSignalAt":"2026-03-15T14:30:00.000Z","isExpired":false,"email":"john@example.com","phoneNumber":"+33612345678","firstName":"John","lastName":"Snow","linkedinUrl":"https://linkedin.com/in/john-snow","linkedinHandle":"john-snow","position":"VP Sales","company":{"name":"Example Inc","domain":"example.com","linkedinUrl":"https://linkedin.com/company/example","numberOfEmployees":250},"owner":{"id":"usr123abc456def789ghi0jk","email":"john@appleseed.com","firstName":"John","lastName":"Appleseed"},"signals":[{"id":"det123abc456def789ghi0jk","signalType":"new_job","detectedAt":"2026-03-10T08:00:00.000Z","signalDate":"2026-03-05T00:00:00.000Z","agent":{"id":"agt123abc456def789ghi0jk","name":"Job Updates"},"data":{"previous_company":"Old Corp","previous_position":"Director","new_company":"Example Inc","new_position":"VP Sales"},"agentType":"job_update"}]}}}}}}},"400":{"description":"Bad request - invalid parameters, multiple fields provided, or owner not a workspace member.","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"},"details":{"type":"object","properties":{"errors":{"type":"object"}}}}},"examples":{"invalid_status":{"summary":"Invalid status value","value":{"error":"Invalid query parameters","details":{"errors":{"status":["Invalid enum value. Expected 'pending' | 'contacted_email' | ..."]}}}},"owner_not_member":{"summary":"Owner email not a workspace member","value":{"error":"Owner email does not belong to a workspace member"}}}}}},"401":{"description":"Unauthorized - invalid or missing API key.","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"}}},"examples":{"missing_key":{"summary":"Missing Authorization header","value":{"error":"Missing or invalid Authorization header"}},"invalid_key":{"summary":"Invalid API key","value":{"error":"Invalid API key"}}}}}},"404":{"description":"Not found - lead does not exist in the workspace.","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"}}},"examples":{"default":{"summary":"Lead not found","value":{"error":"Lead not found"}}}}}},"429":{"description":"Too Many Requests - rate limit exceeded. Retry after the window resets.","headers":{"X-RateLimit-Limit":{"description":"Maximum requests allowed in the current window","schema":{"type":"integer","example":100}},"X-RateLimit-Remaining":{"description":"Requests remaining in the current window","schema":{"type":"integer","example":0}}},"content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"}}},"examples":{"default":{"summary":"Rate limit exceeded","value":{"error":"Rate limit exceeded. Try again later."}}}}}},"500":{"description":"Internal server error - an unexpected error occurred while processing the update.","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"}}},"examples":{"default":{"summary":"Internal error","value":{"error":"An error occurred while updating the lead"}}}}}}}}},"/v2/contents/{id}":{"get":{"tags":["V2 Contents"],"summary":"Get a content item","description":"Returns a single content item by its numeric SQL id.\n\n**Important:** the `id` path parameter is a numeric SQL identifier that is environment-specific (prod only). It is not portable across environments. Pass the top-level `id` returned by `POST /v2/contents/query`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"Numeric SQL id of the content item (the `id` returned by the list endpoint). Environment-specific, prod only, not portable across environments.","schema":{"type":"integer","minimum":1}},{"name":"response_format","in":"query","description":"Controls how much detail the `data` field includes.\n\n- `normalized` (default): a clean, stable projection of the content — see `data` in the response schema.\n- `concise`: `data` is omitted entirely.\n- `detailed`: deprecated alias of `normalized`, kept for backward compatibility.","schema":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized"}}],"responses":{"200":{"description":"Content item","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"20ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"$ref":"#/components/schemas/V2ContentItem"}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/contents/query":{"post":{"tags":["V2 Contents"],"summary":"Query workspace contents","description":"Returns a paginated list of content items for the authenticated workspace. Filters are passed as a JSON body, so identifier arrays (`company_domain`, `company_linkedin_handle`, `company_linkedin_url`) are not bound by URL length limits.\n\nAuthenticate with a `sk_live_` API key.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2ContentsQueryBody"}}}},"responses":{"200":{"description":"Paginated list of contents","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"35ms"}},"X-Total-Count":{"description":"Total number of items matching the query","schema":{"type":"integer","example":150}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":6}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2ContentsPaginatedResponse"}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/content-requests":{"get":{"tags":["V2 Content Requests"],"summary":"List workspace content requests","description":"Returns a paginated list of content requests for the authenticated workspace.\n\nA **content request** represents an asynchronous enrichment or scraping job (e.g. account mapping, top-account content ingestion). The `stage` field tracks its progress.\n\nBy default, completed requests are excluded. Pass `stage[]=completed` to include them.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","description":"Page number (starts at 1). Defaults to 1.","schema":{"type":"integer","minimum":1,"default":1}},{"name":"page_size","in":"query","description":"Number of items per page. Defaults to 25. Maximum: 100.","schema":{"type":"integer","minimum":1,"maximum":100,"default":25}},{"name":"date_from","in":"query","description":"Filter by creation date on or after this date (ISO 8601).","schema":{"type":"string","format":"date-time"}},{"name":"date_to","in":"query","description":"Filter by creation date on or before this date (ISO 8601).","schema":{"type":"string","format":"date-time"}},{"name":"type","in":"query","description":"Filter by request type.","schema":{"type":"string","enum":["account_mapping","top_account_content"]}},{"name":"stage[]","in":"query","description":"Filter by stage. Repeatable. Defaults to all stages except `completed`.","style":"form","explode":true,"schema":{"type":"array","items":{"type":"string","enum":["account_mapping_ready","account_mapping_in_progress","account_mapping_ingestion_ready","account_mapping_ingestion_in_progress","account_mapping_failed","completed","top_account_content_mapping_in_progress","top_account_content_scraping_ready","top_account_content_scraping_starting","top_account_content_scraping_in_progress","top_account_content_failed"]}}},{"name":"company_id","in":"query","description":"Filter by the company's ID in Sillage. When present, takes priority over all human-identifier params below.","schema":{"type":"integer","minimum":1}},{"name":"company_domain","in":"query","description":"Filter by company domain (e.g. `acme.com`). Comma-separated or repeatable. Maximum 100 values. See `company_id` for tier priority.","style":"form","explode":false,"schema":{"type":"array","items":{"type":"string"},"maxItems":100}},{"name":"company_linkedin_handle","in":"query","description":"Filter by company LinkedIn handle. Comma-separated or repeatable. Maximum 100 values. See `company_id` for tier priority.","style":"form","explode":false,"schema":{"type":"array","items":{"type":"string"},"maxItems":100}},{"name":"company_linkedin_url","in":"query","description":"Filter by company LinkedIn URL. Comma-separated or repeatable. Maximum 100 values. See `company_id` for tier priority.","style":"form","explode":false,"schema":{"type":"array","items":{"type":"string"},"maxItems":100}}],"responses":{"200":{"description":"Paginated list of content requests","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"35ms"}},"X-Total-Count":{"description":"Total number of items matching the query","schema":{"type":"integer","example":42}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":2}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2ContentRequestsPaginatedResponse"}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/content-requests/{id}":{"get":{"tags":["V2 Content Requests"],"summary":"Get a content request","description":"Returns a single content request by its numeric SQL id.\n\n**Important:** the `id` path parameter is a numeric SQL identifier that is environment-specific (prod only). It is not portable across environments. Pass the top-level `id` returned by `GET /v2/content-requests`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"Numeric SQL id of the content request (the `id` returned by the list endpoint). Environment-specific, prod only, not portable across environments.","schema":{"type":"integer","minimum":1}}],"responses":{"200":{"description":"Content request item","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"20ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"$ref":"#/components/schemas/V2ContentRequestItem"}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/content-requests/query":{"post":{"tags":["V2 Content Requests"],"summary":"Query workspace content requests (POST body)","description":"POST body alternative to `GET /v2/content-requests`. Accepts the same filters as native JSON arrays.\n\nUse this variant when your identifier arrays exceed URL length limits. For small queries, prefer the GET endpoint.\n\nAuthenticate with a `sk_live_` API key.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2ContentRequestsQueryBody"}}}},"responses":{"200":{"description":"Paginated list of content requests","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"35ms"}},"X-Total-Count":{"description":"Total number of items matching the query","schema":{"type":"integer","example":42}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":2}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2ContentRequestsPaginatedResponse"}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/top-account-list":{"post":{"tags":["V2 Setup"],"summary":"Replace top account list","description":"Replaces the workspace's target account list (TAL) with the provided accounts and begins ingesting them.\n\nThis is an **asynchronous** operation, the 202 response confirms the accounts were accepted. Poll `GET /v2/top-account-list/status` to check progress, then read the enriched results from `GET /v2/top-account-list/accounts` once ingestion completes.\n\n**Persona required:** rejected with `422` and `type: https://docs.getsillage.com/errors/persona-incomplete` when the workspace has no persona whose location resolves to at least one country (or targets `Global`). `detail` names the fix — set a location with `PUT /v2/persona` or `sillage_v2_upsert_persona` before retrying.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["accounts"],"properties":{"accounts":{"type":"array","maxItems":10000,"description":"List of target accounts. Each entry must include at least one of `linkedin_url` or `domain`.","items":{"type":"object","properties":{"linkedin_url":{"type":"string","format":"uri","description":"LinkedIn company URL."},"domain":{"type":"string","minLength":1,"description":"Company domain (e.g. `acme.com`)."},"tier":{"type":"string","enum":["Tier 1","Tier 2","Tier 3"],"description":"Optional tier to set on this account. Left unset, the account is imported without a tier. Stamps `tier_source: manual`, so a later CRM sync can still overwrite it."}}}}}},"examples":{"default":{"summary":"Replace with two accounts","value":{"accounts":[{"domain":"acme.com","tier":"Tier 1"},{"linkedin_url":"https://www.linkedin.com/company/northstar","domain":"northstar.io"}]}}}}}},"responses":{"202":{"description":"Accounts accepted for ingestion","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"40ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["tal_id","accounts","message"],"properties":{"tal_id":{"type":"integer","description":"Identifier of the top account list.","example":42},"accounts":{"type":"array","items":{"type":"object","properties":{"linkedin_url":{"type":"string"},"domain":{"type":"string"},"tier":{"type":"string","enum":["Tier 1","Tier 2","Tier 3"]}}}},"message":{"type":"string","example":"Top account list ingestion queued"}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/top-account-list/accounts":{"get":{"tags":["V2 Setup"],"summary":"List accounts (found only)","description":"Returns a paginated list of **found** accounts from the workspace top account list.\n\nOnly accounts whose enrichment resolved a company record (`status: found`) are included.\nAccounts that could not be matched are available at `GET /v2/top-account-list/accounts/not-found`.\n\nThe partner mirror of this endpoint accepts the same `persona_id` parameter, resolved against the workspace behind `partner_workspace_id`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","description":"Page number (starts at 1). Defaults to 1.","schema":{"type":"integer","minimum":1,"default":1}},{"name":"page_size","in":"query","description":"Number of items per page. Defaults to 25. Maximum: 100.","schema":{"type":"integer","minimum":1,"maximum":100,"default":25}},{"name":"persona_id","in":"query","description":"Only return accounts belonging to this persona, plus any account not yet assigned to one. Omit to return every account. This id is specific to your environment.","schema":{"type":"integer"}}],"responses":{"200":{"description":"Paginated found accounts","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"30ms"}},"X-Total-Count":{"description":"Total number of found accounts matching the query","schema":{"type":"integer","example":87}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":4}}},"content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/V2EnrichedAccount"}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"$ref":"#/components/schemas/V2PaginationMeta"}}}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Unknown `persona_id`."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"post":{"tags":["V2 Setup"],"summary":"Add accounts (batch)","description":"Adds a batch of accounts to the workspace top account list with **merge** semantics.\n\nExisting accounts are preserved. Deduplication is handled automatically by the enrichment pipeline.\n\nThe ingestion runs asynchronously. Poll `GET /v2/top-account-list/status` to check progress, then read the enriched results from `GET /v2/top-account-list/accounts`.\n\n**Persona required:** rejected with `422` and `type: https://docs.getsillage.com/errors/persona-incomplete` when the workspace has no persona whose location resolves to at least one country (or targets `Global`). `detail` names the fix — set a location with `PUT /v2/persona` or `sillage_v2_upsert_persona` before retrying.\n\n**Credits:** accounts added to the list are mapped and their relevant employee profiles' content is analyzed, which consumes credits per account and per analyzed profile. Because this processing is asynchronous, a workspace that runs out of credits does not receive an error here: processing simply pauses until credits are added.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["accounts"],"properties":{"accounts":{"type":"array","maxItems":10000,"description":"Accounts to add. Each entry must include at least one of `linkedin_url` or `domain`.","items":{"type":"object","properties":{"linkedin_url":{"type":"string","format":"uri","description":"LinkedIn company URL."},"domain":{"type":"string","minLength":1,"description":"Company domain (e.g. `acme.com`)."},"tier":{"type":"string","enum":["Tier 1","Tier 2","Tier 3"],"description":"Optional tier to set on this account. Left unset, the account is imported without a tier. Stamps `tier_source: manual`, so a later CRM sync can still overwrite it."}}}}}}}}},"responses":{"202":{"description":"Accounts accepted for ingestion","content":{"application/json":{"schema":{"type":"object","required":["tal_id","accounts","message"],"properties":{"tal_id":{"type":"integer","description":"Identifier of the top account list.","example":42},"accounts":{"type":"array","items":{"type":"object","properties":{"linkedin_url":{"type":"string"},"domain":{"type":"string"},"tier":{"type":"string","enum":["Tier 1","Tier 2","Tier 3"]}}}},"message":{"type":"string"},"warnings":{"type":"array","items":{"type":"string"},"description":"Advisory reminders about the resulting list, e.g. below the recommended 5-20 account band. Omitted when there is nothing to report. Never blocks the write."}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/top-account-list/accounts/not-found":{"get":{"tags":["V2 Setup"],"summary":"List not-found accounts","description":"Returns a paginated list of accounts whose enrichment could not resolve a company record (`status: not_found`).\n\nEach item carries the original `user_input` submitted (company name, domain, or LinkedIn URL), a partial `company` object with whatever data was available, and the `imported_at` timestamp.\n\nFound accounts are available at `GET /v2/top-account-list/accounts`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","description":"Page number (starts at 1). Defaults to 1.","schema":{"type":"integer","minimum":1,"default":1}},{"name":"page_size","in":"query","description":"Number of items per page. Defaults to 25. Maximum: 100.","schema":{"type":"integer","minimum":1,"maximum":100,"default":25}}],"responses":{"200":{"description":"Paginated not-found accounts","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"25ms"}},"X-Total-Count":{"description":"Total number of not-found accounts","schema":{"type":"integer","example":12}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":1}}},"content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["company","user_input","imported_at"],"properties":{"id":{"type":"string","description":"Workspace company document id, if created."},"company":{"type":"object","required":["status"],"properties":{"name":{"type":"string"},"domain":{"type":"string"},"linkedin_url":{"type":"string"},"linkedin_handle":{"type":"string"},"logo_url":{"type":"string"},"status":{"type":"string","enum":["not_found"],"description":"Always `not_found` for this endpoint."}}},"user_input":{"type":"object","description":"The original values submitted when this account was added.","properties":{"company_name":{"type":"string"},"domain":{"type":"string"},"linkedin_url":{"type":"string"},"custom_properties":{"type":"object","additionalProperties":true}}},"imported_at":{"type":"string","format":"date-time","description":"When this account was imported."}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"$ref":"#/components/schemas/V2PaginationMeta"}}}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/top-account-list/accounts/remove":{"post":{"tags":["V2 Setup"],"summary":"Remove accounts (batch)","description":"Removes a batch of accounts from the workspace top account list.\n\nEach item is matched by `linkedin_url` or `domain`. Non-matching items are silently skipped.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["accounts"],"properties":{"accounts":{"type":"array","description":"Accounts to remove.","items":{"type":"object","properties":{"linkedin_url":{"type":"string","format":"uri"},"domain":{"type":"string"}}}}}}}}},"responses":{"200":{"description":"Batch removal result","content":{"application/json":{"schema":{"type":"object","required":["deleted_count","message"],"properties":{"deleted_count":{"type":"integer","description":"Number of accounts removed."},"message":{"type":"string"}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/top-account-list/status":{"get":{"tags":["V2 Setup"],"summary":"Get ingestion status","description":"Returns the current state of the latest top account list ingestion.\n\nPoll this endpoint after calling `POST /v2/top-account-list` or `POST /v2/top-account-list/accounts` to track progress.","security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Current ingestion status","content":{"application/json":{"schema":{"type":"object","required":["state","total_accounts"],"properties":{"state":{"type":"string","enum":["queued","processing","completed","failed"],"description":"Current state of the ingestion."},"total_accounts":{"type":"integer","minimum":0,"description":"Number of accounts processed in the last ingestion."}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/top-account-list/count":{"get":{"tags":["V2 Setup"],"summary":"Count accounts (found only)","description":"Returns the total number of **found** accounts in the workspace top account list.\n\nOnly accounts whose enrichment resolved a company record (`status: found`) are counted.\nNot-found accounts are excluded from this count.","security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Found account count","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"20ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["total"],"properties":{"total":{"type":"integer","minimum":0,"description":"Number of found accounts in the top account list."}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/top-account-list/accounts/{id}":{"delete":{"tags":["V2 Setup"],"summary":"Remove account by id","description":"Removes a single account from the workspace top account list by its integer `id` (the `id` field returned by `GET /v2/top-account-list/accounts`). Returns 404 if no matching account is found or the id belongs to a different workspace.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"integer","minimum":1},"description":"The company's ID in Sillage, as returned by the `id` field in the list endpoint."}],"responses":{"200":{"description":"Account removed","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["removed"],"properties":{"removed":{"type":"boolean","description":"Always `true` in a 200 response."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/persona":{"get":{"tags":["V2 Setup"],"summary":"Get workspace persona","description":"Returns the workspace's current persona (ideal customer profile targeting criteria). Returns `{ data: null }` with HTTP 200 when no persona has been configured yet.\n\n**Deprecated:** only ever reads the oldest persona, which no longer reflects workspaces with more than one business line. Use `GET /v2/personas` and `GET /v2/personas/{persona_id}` instead. Removal is tracked in SIL-1798.","deprecated":true,"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Persona retrieved (or not yet configured)","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"25ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"nullable":true,"type":"object","properties":{"id":{"type":"integer","description":"Identifier of the persona.","example":1234},"job_title":{"type":"array","items":{"type":"string"},"nullable":true},"exclude_job_title":{"type":"array","items":{"type":"string"},"nullable":true},"location":{"type":"array","items":{"type":"string"},"nullable":true},"headcount":{"type":"array","items":{"type":"string"},"nullable":true},"industry":{"type":"array","items":{"type":"string"},"nullable":true},"seniority":{"type":"array","items":{"type":"string"},"nullable":true},"additional_info":{"type":"string","nullable":true},"tag":{"type":"string","nullable":true,"description":"Short free-form label you can set to recognise this persona in your own systems. Never used for targeting, and unique across the personas of a workspace."}}}}},"examples":{"configured":{"summary":"Persona configured","value":{"data":{"id":1234,"job_title":["VP Sales","Head of Sales"],"exclude_job_title":null,"location":["France","Germany"],"headcount":null,"industry":null,"seniority":["vp","director"],"additional_info":null,"tag":"enterprise-emea"}}},"notConfigured":{"summary":"No persona yet","value":{"data":null}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"put":{"tags":["V2 Setup"],"summary":"Upsert workspace persona","description":"Creates or replaces the workspace's persona (ideal customer profile targeting criteria).\n\nThis is a **replace** operation, a second `PUT` updates the same persona record rather than creating a duplicate. Every field except `job_title` and `location` is optional; omitting an optional field leaves it unset. `job_title` and `location` are required and must each contain at least one value — `location` is what lets account mapping and content generation know which countries to search in.\n\n**Deprecated:** only ever writes the oldest persona, so it cannot create a second business line. Use `POST /v2/personas` to create one and `PATCH /v2/personas/{persona_id}` to update one. Removal is tracked in SIL-1798.","deprecated":true,"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["job_title","location"],"properties":{"job_title":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Required. Target job titles — at least one value."},"exclude_job_title":{"type":"array","items":{"type":"string"},"description":"Job titles to exclude."},"location":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Required. Target locations — at least one value. Use country or region names (e.g. \"EMEA\"); a city-only list saves but will not match any country, so account mapping will not run for it."},"headcount":{"type":"array","items":{"type":"string"},"description":"Target headcount ranges (enum values)."},"industry":{"type":"array","items":{"type":"string"},"description":"Target industries."},"seniority":{"type":"array","items":{"type":"string"},"description":"Target seniority levels (enum values)."},"additional_info":{"type":"string","description":"Additional free-text persona context."},"tag":{"type":"string","maxLength":255,"description":"Short free-form label you can set to recognise this persona in your own systems. Never used for targeting. Two personas of the same workspace cannot share a tag — reusing one returns 409. Omit it to leave the persona untagged."}}},"examples":{"default":{"summary":"VP Sales persona","value":{"job_title":["VP Sales","Head of Sales"],"seniority":["vp","director"],"location":["France","Germany"],"tag":"enterprise-emea"}}}}}},"responses":{"200":{"description":"Persona upserted","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"25ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id"],"properties":{"id":{"type":"integer","description":"Identifier of the persona.","example":1234}}},"warnings":{"type":"array","items":{"type":"string"},"description":"Advisory warnings about the submitted persona, e.g. a missing job_title/location or a location that could not be resolved to a country (account mapping will not run for it). Omitted when there is nothing to report. Never blocks the write — the persona above is already saved."}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"409":{"$ref":"#/components/responses/V2Conflict"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/personas":{"get":{"tags":["V2 Setup"],"summary":"List personas","description":"Returns every one of the workspace's personas (business lines), paginated. Archived personas are excluded.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","description":"Page number (starts at 1). Defaults to 1.","schema":{"type":"integer","minimum":1,"default":1}},{"name":"page_size","in":"query","description":"Number of items per page. Defaults to 25. Maximum: 100.","schema":{"type":"integer","minimum":1,"maximum":100,"default":25}}],"responses":{"200":{"description":"Paginated list of personas","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Total-Count":{"description":"Total number of personas","schema":{"type":"integer","example":3}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":1}}},"content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/V2Persona"}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"$ref":"#/components/schemas/V2PaginationMeta"}}}}},"examples":{"default":{"summary":"Two personas","value":{"data":[{"id":1234,"job_title":["VP Sales","Head of Sales"],"exclude_job_title":null,"location":["France","Germany"],"headcount":null,"industry":null,"seniority":["vp","director"],"additional_info":null,"tag":"enterprise-emea"},{"id":1235,"job_title":["SDR"],"exclude_job_title":null,"location":["United States"],"headcount":null,"industry":null,"seniority":null,"additional_info":null,"tag":"smb-us"}],"meta":{"pagination":{"page":1,"page_size":25,"page_count":1,"total":2}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Invalid `page` or `page_size` query parameter."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"post":{"tags":["V2 Setup"],"summary":"Create a persona","description":"Creates a new persona (business line) for the workspace — unlike `PUT /v2/persona`, this always creates a new record rather than replacing an existing one, so it is how an integrator sets up a second business line.\n\nThere is no limit on the number of personas a workspace can create through this endpoint. Every field except `job_title` and `location` is optional. `job_title` and `location` are required and must each contain at least one value — `location` is what lets account mapping and content generation know which countries to search in.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2PersonaBody"},"examples":{"default":{"summary":"A second business line","value":{"job_title":["SDR"],"location":["United States"],"tag":"smb-us"}}}}}},"responses":{"201":{"description":"Persona created","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2PersonaWriteResponse"}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"409":{"$ref":"#/components/responses/V2Conflict"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/personas/{persona_id}":{"get":{"tags":["V2 Setup"],"summary":"Get one persona","description":"Returns one of the workspace's personas by id. 404 if the id is unknown, archived, or belongs to another workspace.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"persona_id","in":"path","required":true,"description":"ID of the persona, as returned by `GET /v2/personas`. This ID is specific to your environment.","schema":{"type":"integer"}}],"responses":{"200":{"description":"Persona retrieved","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"$ref":"#/components/schemas/V2Persona"}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"patch":{"tags":["V2 Setup"],"summary":"Update a persona","description":"Partially updates one persona. Every field is optional, but at least one must be sent. Fields left out are unchanged; the others behave exactly like `PUT /v2/persona` (e.g. `location` must keep at least one value if sent). Updating one persona never touches another.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"persona_id","in":"path","required":true,"description":"ID of the persona, as returned by `GET /v2/personas`. This ID is specific to your environment.","schema":{"type":"integer"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2PersonaPatchBody"},"examples":{"default":{"summary":"Change the location only","value":{"location":["Germany"]}}}}}},"responses":{"200":{"description":"Persona updated","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2PersonaWriteResponse"}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"$ref":"#/components/responses/V2Conflict"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/setup-state":{"get":{"tags":["V2 Setup"],"summary":"Get workspace setup state","description":"Returns workspace setup completeness in one call: the 4 legacy boolean signals plus a per-dimension checklist.\n\nThe checklist covers `persona`, `accounts`, `agents`, and `contents`. Each dimension has a `status` (`ok`, `warning`, or `blocked`), a plain-language `message`, and, when relevant, a `recommended_next_tool` naming exactly what to call next.\n\nA `blocked` status on `contents` distinguishes two cases that used to be indistinguishable: the contents feature is not enabled for this workspace (contact Sillage) versus the feature being enabled with nothing generated yet (`warning`).","security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Setup state retrieved","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"30ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["persona_set","list_uploaded","ingestion_complete","has_contents","checklist"],"properties":{"persona_set":{"type":"boolean","description":"Whether a persona has been configured for this workspace."},"list_uploaded":{"type":"boolean","description":"Whether at least one account is in the top-account list."},"ingestion_complete":{"type":"boolean","description":"Whether ingestion of the top-account list has completed (state = 'completed')."},"has_contents":{"type":"boolean","description":"Whether at least one generated content item exists for this workspace."},"checklist":{"type":"object","required":["persona","accounts","agents","contents"],"properties":{"persona":{"type":"object","required":["status","message","job_title_set","location_set"],"properties":{"status":{"type":"string","enum":["ok","warning","blocked"]},"message":{"type":"string"},"recommended_next_tool":{"type":"string"},"job_title_set":{"type":"boolean"},"location_set":{"type":"boolean"}}},"accounts":{"type":"object","required":["status","message","count","ingestion_state","has_unresolved_accounts"],"properties":{"status":{"type":"string","enum":["ok","warning","blocked"]},"message":{"type":"string"},"recommended_next_tool":{"type":"string"},"count":{"type":"integer","minimum":0},"ingestion_state":{"type":"string","enum":["queued","processing","completed","failed"]},"has_unresolved_accounts":{"type":"boolean"}}},"agents":{"type":"object","required":["status","message","count","missing_priority_types"],"properties":{"status":{"type":"string","enum":["ok","warning","blocked"]},"message":{"type":"string"},"recommended_next_tool":{"type":"string"},"count":{"type":"integer","minimum":0},"missing_priority_types":{"type":"array","items":{"type":"string","enum":["keyword_detection","competitor","partner","customer","influencer","champion","job_update"]},"description":"Recommended agent types (job update, competitor, customer, keyword detection) not yet present, in priority order."}}},"contents":{"type":"object","required":["status","message","has_contents"],"properties":{"status":{"type":"string","enum":["ok","warning","blocked"]},"message":{"type":"string"},"recommended_next_tool":{"type":"string"},"has_contents":{"type":"boolean"}}}}}}},"examples":{"halfSetUp":{"summary":"Thin persona, 1 account, 0 agents","value":{"persona_set":true,"list_uploaded":true,"ingestion_complete":true,"has_contents":false,"checklist":{"persona":{"status":"warning","message":"Persona is missing location. Without it, account mapping and employee-level content will not run correctly. Call sillage_v2_upsert_persona to complete it.","recommended_next_tool":"sillage_v2_upsert_persona","job_title_set":true,"location_set":false},"accounts":{"status":"warning","message":"1 account(s) is below the recommended minimum of 5. Call sillage_v2_add_top_accounts to add more.","recommended_next_tool":"sillage_v2_add_top_accounts","count":1,"ingestion_state":"completed","has_unresolved_accounts":false},"agents":{"status":"blocked","message":"No agents created yet. Call sillage_v2_create_agent to start detecting signals (recommended minimum: 3).","recommended_next_tool":"sillage_v2_create_agent","count":0,"missing_priority_types":["job_update","competitor","customer","keyword_detection"]},"contents":{"status":"warning","message":"The contents feature is enabled but nothing has been generated yet. Call sillage_v2_get_requests_status to check whether account mapping or content generation is still in progress.","recommended_next_tool":"sillage_v2_get_requests_status","has_contents":false}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/credits/balance":{"get":{"tags":["V2 Credits"],"summary":"Get workspace credit balance","description":"Returns how many credits your workspace can currently spend, plus your three most recently added credit batches, newest first.\n\n`available_credits` is your spendable total, in whole credits. Each entry in `batches` is one grant or purchase still contributing credits: its own remaining amount (`remaining_credits`), when it expires (`expires_at`), where it came from (`source`: `\"purchase\"`, `\"plan_grant\"`, `\"manual\"`, or `\"reward\"`), and when it was added (`created_at`).\n\n`batches` is capped at your three most recent additions and is **not** the order credits are spent in — spending always consumes the soonest-expiring batch first. Use it to confirm a purchase landed, not to reconcile a balance: `available_credits` is the authority, and it can exceed the sum of the batches shown.\n\nTo confirm one specific payment has been credited, match `stripe_payment_intent_id` against the PaymentIntent of that payment. It is unique per batch, so it identifies the purchase exactly — unlike an amount and a timestamp, which two identical purchases would share.\n\nIf your workspace is billed through a partner rather than directly, this always returns `available_credits: 0` with an empty `batches` array — that is expected, not an error. Partner-billed workspaces are never limited by a credit balance; their usage is invoiced to the partner separately.","security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Credit balance retrieved","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"30ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["available_credits","batches"],"properties":{"available_credits":{"type":"integer","description":"Whole credits your workspace can spend right now. Always 0 for a partner-billed workspace."},"batches":{"type":"array","description":"Your three most recently added active batches, newest first. Not consumption order, and not the full list. Always empty for a partner-billed workspace.","items":{"type":"object","required":["id","remaining_credits","expires_at","source","created_at","stripe_payment_intent_id"],"properties":{"id":{"type":"integer"},"remaining_credits":{"type":"integer","description":"Whole credits still left in this batch."},"expires_at":{"type":"string","format":"date-time","description":"When this batch stops counting toward the balance."},"source":{"type":"string","enum":["purchase","plan_grant","manual","reward"],"description":"How this batch was added to the workspace."},"created_at":{"type":"string","format":"date-time"},"stripe_payment_intent_id":{"type":"string","nullable":true,"description":"The Stripe PaymentIntent that paid for this batch. Null unless `source` is `\"purchase\"`. Use it to match a batch to a payment you just made."}}}}}},"examples":{"withActiveBatches":{"summary":"Two active batches","value":{"available_credits":1250,"batches":[{"id":42,"remaining_credits":250,"expires_at":"2026-09-01T00:00:00.000Z","source":"purchase","created_at":"2026-06-01T00:00:00.000Z","stripe_payment_intent_id":"pi_3QxYzAbCdEfGhIjK0LmNoPqR"},{"id":41,"remaining_credits":1000,"expires_at":"2026-10-15T00:00:00.000Z","source":"plan_grant","created_at":"2026-07-15T00:00:00.000Z","stripe_payment_intent_id":null}]}},"partnerBilled":{"summary":"Partner-billed workspace — no stock, not an error","value":{"available_credits":0,"batches":[]}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/requests-status":{"get":{"tags":["Signal Runs"],"summary":"Get in-flight workspace requests","description":"Returns all work currently being processed in your workspace as a single\n`requests` list, newest first. Each item carries a `type` field telling you\nwhat kind of work it is: `\"account_mapping\"`, `\"top_account_content\"`, or\n`\"signal\"`.\n\nOnly pending and in-progress items are returned — failed and completed requests\nare excluded from this snapshot.\n\nEach item carries a `status` field (`\"pending\"` or `\"in_progress\"`) and a\nplain-language `label` safe to show directly to a user.\n\nItems with type `account_mapping` or `top_account_content` carry the company\nthey are running for and the timestamps.\n\nItems with type `signal` carry a `companies` array (the accounts being scanned)\nand a `scope` field: `\"company\"` when the run targets specific accounts, `\"workspace\"`\nwhen it spans the whole workspace (e.g. a job-change run with no per-account scope).\n\n`meta.in_flight_total` is the true count of pending and in-progress items.\n\nThe snapshot is paginated for extreme cases (e.g. a large account list being\ningested): one call returns up to `page_size` items (default and maximum 500,\nnewest first). When `meta.page_count` is greater than 1, request the remaining\npages with `?page=2`, `?page=3`, and so on.\n\nAn empty `requests` list means nothing is running — not an error.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number. Only needed when a previous response reported `meta.page_count` greater than 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":500,"default":500},"description":"Items per page."}],"responses":{"200":{"description":"In-flight work across the workspace, newest first","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"object","required":["requests"],"properties":{"requests":{"type":"array","description":"All in-flight items, newest first, mixed kinds — branch on `type`.","items":{"oneOf":[{"allOf":[{"$ref":"#/components/schemas/V2ContentRequestStatusItem"},{"type":"object","required":["type"],"properties":{"type":{"type":"string","enum":["account_mapping","top_account_content"],"description":"What kind of work this item is."}}}]},{"allOf":[{"$ref":"#/components/schemas/V2SignalRequestStatusItem"},{"type":"object","required":["type"],"properties":{"type":{"type":"string","enum":["signal"],"description":"What kind of work this item is."}}}]}]}}}},"meta":{"type":"object","required":["in_flight_total","page","page_size","page_count"],"properties":{"in_flight_total":{"type":"integer","description":"True total of in-flight items, regardless of pagination.","example":3},"page":{"type":"integer","description":"Current page.","example":1},"page_size":{"type":"integer","description":"Items per page.","example":500},"page_count":{"type":"integer","description":"Total number of pages. Greater than 1 only in extreme cases — fetch the remaining pages to see everything.","example":1}}}}},"example":{"data":{"requests":[{"type":"signal","id":5,"status":"in_progress","label":"Detecting signals","created_at":"2026-06-30T08:05:00.000Z","updated_at":"2026-06-30T08:05:00.000Z","scope":"company","companies":[{"id":88,"name":"Acme","domain":"acme.com"}]},{"type":"account_mapping","id":12,"status":"in_progress","label":"Mapping the account","created_at":"2026-06-30T08:00:00.000Z","updated_at":"2026-06-30T08:01:00.000Z","company":{"id":88,"name":"Acme","domain":"acme.com"}}]},"meta":{"in_flight_total":2,"page":1,"page_size":500,"page_count":1}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/workspace/signal-runs":{"get":{"tags":["Signal Runs"],"summary":"List in-flight signal runs","description":"Returns all signal runs that are currently in progress for the authenticated workspace.\n\nEach item carries a `companies` array (the accounts being scanned) and a `scope` field:\n`\"company\"` when the run targets specific accounts, `\"workspace\"` when it spans the whole\nworkspace.\n\nThis endpoint returns a snapshot — it is not paginated. An empty `data` array means no\nruns are currently in progress.","security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"List of in-flight signal runs","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/V2SignalRequestStatusItem"}}}},"example":{"data":[{"id":5,"status":"in_progress","label":"Detecting signals","created_at":"2026-06-30T08:05:00.000Z","updated_at":"2026-06-30T08:05:00.000Z","scope":"company","companies":[{"id":88,"name":"Acme","domain":"acme.com"}]}]}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"post":{"tags":["Signal Runs"],"summary":"Launch a signal run","description":"Starts a detection run for the agent across your target accounts. The signal\ntype is derived automatically from the agent — no `signal_key` is needed.\nWatchlist agents launch both inbound and outbound directions; keyword agents\nlaunch one run. Each direction returns one element in the response array.\nThe run starts immediately and responds with `202 Accepted`.\n\nChampion-tracking agents can also be launched here. They always return a\nsingle-element response array, ignore `parameters` entirely (there is no\n`lookback_days` to set), and re-check the people on the bound watchlist for\nrecent job changes — accounts checked in the last 30 days are skipped.\n\n## Checking progress\n\nUse each `signal_request_id` from the response array with\n`GET /api/v2/workspace/signal-runs/{id}` to follow that run until `stage` is\n`completed` (or `completed_partial` if some accounts could not be processed).\n\n## One run at a time\n\nAn agent returns `409 Conflict` if you launch it while any of its runs is still\nin progress. Poll the run to completion first, then launch again. Once a run has\nfinished, relaunching is safe — the same matches will not be created twice.\n\n## Insufficient credits\n\nA keyword agent returns `402 Payment Required` if your workspace does not have\nenough credits to pay for at least one detection. Nothing is started in that\ncase — top up your credits and try again.\n\n## Run temporarily unavailable\n\nA keyword agent returns `500 Internal Server Error` if this run type is not yet\navailable for your workspace. Nothing is started in that case — this is on our\nend, please contact support if you keep seeing it.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["agent_id"],"properties":{"agent_id":{"type":"integer","description":"The ID of the agent to run, from your Sillage workspace. This ID is specific to your environment.","example":42},"parameters":{"type":"object","description":"Optional run parameters. Keyword and interaction agents accept `lookback_days`; champion-tracking agents ignore this field.","properties":{"lookback_days":{"type":"integer","minimum":1,"maximum":180,"description":"How many days back to scan for matches, counted from now. Defaults to 90. Keyword and interaction agents only."}}}}}}}},"responses":{"202":{"description":"Signal run accepted and enqueued","content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2SignalRunLaunchResponse"},"examples":{"keyword":{"summary":"Keyword agent — one run","value":[{"signal_request_id":12345,"stage":"running"}]},"watchlist":{"summary":"Watchlist agent — two runs (inbound + outbound)","value":[{"signal_request_id":12345,"stage":"running"},{"signal_request_id":12346,"stage":"running"}]},"champion":{"summary":"Champion-tracking agent — one run","value":[{"signal_request_id":12347,"stage":"running"}]}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"402":{"$ref":"#/components/responses/V2PaymentRequired"},"403":{"description":"Your workspace is blocked, so no run can be launched. Nothing was started.","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"$ref":"#/components/responses/V2Conflict"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/workspace/signal-runs/{id}":{"get":{"tags":["Signal Runs"],"summary":"Poll a signal run","description":"Returns the current status of a run.\n\nThe `id` is the `signal_request_id` returned when you launched the run.\nRuns that belong to a different workspace are not accessible and return 404.\n\nFor a champion-tracking run, `stage` moves directly from `running` to\n`completed` (or `failed`) once the watchlist has been re-checked — there is no\n`completed_partial` state for this agent type.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"The numeric `signal_request_id` returned by the launch endpoint.","schema":{"type":"integer"}}],"responses":{"200":{"description":"Signal run status","content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2SignalRunPollResponse"},"examples":{"running":{"summary":"Still running","value":{"signal_request_id":12345,"stage":"running","metadata":null}},"completed":{"summary":"Completed","value":{"signal_request_id":12345,"stage":"completed","metadata":null}},"completed_partial":{"summary":"Completed with incomplete coverage","value":{"signal_request_id":12345,"stage":"completed_partial","metadata":{"failed":{"dropped_account_ids":[202,203]}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"403":{"$ref":"#/components/responses/V2Forbidden"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/partner/usage":{"get":{"tags":["Partner"],"summary":"Get partner usage","description":"Returns real-time consumption for your partner account, in credits only (no currency\namounts), broken down per workspace and per product.\n\nWhen both `date_from` and `date_to` are provided, they may span at most 3 months —\na wider window is rejected with a 422. When only one of the two is provided, the other\nbound is derived 3 calendar months away (UTC): `date_from` alone means\n`date_to = date_from + 3 months`, and `date_to` alone means\n`date_from = date_to - 3 months`. When both are omitted, the window is the current\ncalendar month to date (UTC).\n\nEvery level of the response carries a `credits_by_status` object: credits grouped by\nwhere they are in the billing lifecycle. Possible keys:\n\n- `held` — reserved for an action still in progress; not final and not billable yet.\n- `invoiceable` — the action completed; these credits will appear on your next invoice.\n- `invoice_edited` — an invoice covering these credits has been issued to you.\n- `invoice_paid` — the invoice covering these credits has been paid.\n- `released` — the reservation was cancelled because the action did not complete; you\n  are never billed for these credits.\n\nA status key is only present when the period contains credits in that status.","security":[{"PartnerMasterKeyAuth":[]}],"parameters":[{"name":"date_from","in":"query","required":false,"description":"ISO 8601 timestamp. Include consumption at or after this date. When omitted, derived as 3 calendar months before `date_to` if `date_to` is provided; otherwise defaults to the start of the current calendar month (UTC).","schema":{"type":"string","format":"date-time"}},{"name":"date_to","in":"query","required":false,"description":"ISO 8601 timestamp. Include consumption strictly before this date. When omitted, derived as 3 calendar months after `date_from` if `date_from` is provided; otherwise defaults to now. When both dates are provided, `date_to` must be at most 3 months after `date_from`.","schema":{"type":"string","format":"date-time"}}],"responses":{"200":{"description":"Partner usage for the requested period","content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2PartnerUsageResponse"},"example":{"workspaces":[{"id":88,"credits_by_status":{"invoiceable":12.5,"held":1},"by_product":[{"product":"champion_enrichment","credits_by_status":{"invoiceable":8,"held":1}},{"product":"keyword_signal","credits_by_status":{"invoiceable":4.5}}]},{"id":91,"credits_by_status":{"invoice_paid":3},"by_product":[{"product":"account_mapping_launch","credits_by_status":{"invoice_paid":3}}]}],"credits_by_status":{"invoiceable":12.5,"held":1,"invoice_paid":3}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"$ref":"#/components/responses/V2UnprocessableEntity"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/workspace/signals/query":{"post":{"tags":["Signals"],"summary":"List signal detections","description":"Returns a cursor-paginated list of published signal detections for the authenticated workspace,\nsorted by detection date descending (most recent first).\n\nThis endpoint uses cursor pagination instead of offset pagination. Pass the `next_cursor`\nfrom one response as the `cursor` field of the next request to advance through the list.\nWhen `has_more` is false, you have reached the end.\n\nUse `GET /v2/workspace/signals/count` with the same filters to get the total count.\n\nNote: this is a deliberate divergence from the standard v2 offset-pagination envelope.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":false,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2SignalsQueryBody"}}}},"responses":{"200":{"description":"Cursor-paginated list of signal detections, sorted by detection date descending (most recent first).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2SignalListResponse"},"examples":{"sample":{"summary":"One keyword detection","value":{"data":[{"id":101,"signal_type":"keywordDetection","data":{"content_id":5100,"author":{"type":"profile","full_name":"Jane Doe","headline":"VP Product at Acme","linkedin_url":"https://linkedin.com/in/janedoe"},"keywords_found":["AI"]},"detected_at":"2026-06-01T10:00:00.000Z","signal_date":null,"lead_id":456,"company_id":789,"agent_id":12}],"meta":{"next_cursor":"eyJkZXRlY3RlZEF0IjoiMjAyNi0wNi0wMVQxMDowMDowMC4wMDBaIiwiaWQiOjEwMX0=","has_more":true}}},"watchlistComment":{"summary":"One watchlist comment detection","value":{"data":[{"id":102,"signal_type":"competitorInboundComment","data":{"interaction":{"type":"comment","content_id":5001,"author":{"full_name":"Jane Doe","linkedin_url":"https://linkedin.com/in/janedoe","headline":"VP Product at Acme"}},"post":{"content_id":5002,"author":{"full_name":"John Smith","linkedin_url":"https://linkedin.com/in/johnsmith","headline":"Head of Sales at Widgets"}}},"detected_at":"2026-06-01T10:00:00.000Z","signal_date":"2026-05-28T08:12:00.000Z","lead_id":456,"company_id":789,"agent_id":12}],"meta":{"next_cursor":null,"has_more":false}}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"403":{"$ref":"#/components/responses/V2Forbidden"},"404":{"description":"Returned when string company identifier(s) (`company_domain`, `company_linkedin_handle`, or `company_linkedin_url`) were supplied and none of them resolved to a known company in your workspace. Note: `company_id` is taken at face value and never triggers a `404` — an ID that does not belong to your workspace returns an empty result set instead."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/workspace/signals/count":{"get":{"tags":["Signals"],"summary":"Count signal detections","description":"Returns the total number of published signal detections matching the given filters.\n\nAccepts the same filter parameters as `POST /v2/workspace/signals/query`.\nUse this endpoint to get a total before or alongside paginating the list.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"signal_start_date","in":"query","required":false,"description":"Count detections whose signal date is on or after this timestamp (ISO 8601 with UTC offset). Defaults to 90 days before now. Cannot go further back than 180 days — an older value is clamped to that limit.","schema":{"type":"string","format":"date-time"}},{"name":"signal_end_date","in":"query","required":false,"description":"Count detections whose signal date is on or before this timestamp (ISO 8601 with UTC offset).","schema":{"type":"string","format":"date-time"}},{"name":"detection_start_date","in":"query","required":false,"description":"Count detections that were first seen on or after this timestamp (ISO 8601 with UTC offset).","schema":{"type":"string","format":"date-time"}},{"name":"detection_end_date","in":"query","required":false,"description":"Count detections that were first seen on or before this timestamp (ISO 8601 with UTC offset).","schema":{"type":"string","format":"date-time"}},{"name":"agent_id","in":"query","required":false,"description":"Count detections produced by a specific agent. Pass the numeric `agent_id` returned on each detection in the list response.","schema":{"type":"integer"}},{"name":"signal_run_id","in":"query","required":false,"description":"Count detections from a specific run. Pass the numeric run id returned by the signal-runs endpoint.","schema":{"type":"integer"}},{"name":"company_id","in":"query","required":false,"description":"Count detections for a specific company. Pass the numeric `company_id` returned in signal items — the same company ID used by `GET /v2/companies/{id}`. Taken at face value — no lookup is performed, so an ID that does not belong to your workspace returns a zero count rather than a `404`.","schema":{"type":"integer"}},{"name":"company_domain","in":"query","required":false,"description":"Count detections for companies on your top-account list matching this domain. Accepts a comma-separated list for OR filtering across multiple companies. Returns `404` when none of the supplied values resolve to a known company on your top-account list.","schema":{"type":"string"},"example":"acme.com,widgets.io"},{"name":"company_linkedin_handle","in":"query","required":false,"description":"Count detections for companies on your top-account list matching this LinkedIn handle. Accepts a comma-separated list for OR filtering across multiple companies. Returns `404` when none of the supplied values resolve to a known company on your top-account list.","schema":{"type":"string"},"example":"acme-corp,widgets-io"},{"name":"company_linkedin_url","in":"query","required":false,"description":"Count detections for companies on your top-account list matching this LinkedIn URL. Accepts a comma-separated list for OR filtering across multiple companies. Returns `404` when none of the supplied values resolve to a known company on your top-account list.","schema":{"type":"string"},"example":"https://www.linkedin.com/company/acme-corp,https://www.linkedin.com/company/widgets-io"},{"name":"lead_id","in":"query","required":false,"description":"Filter to signals linked to a specific lead. Use the `lead_id` returned by the signals endpoints; resolve details via `GET /v2/leads/{id}`. Only matches detections directly linked to the lead — not signals attributed to that lead through fallback matching.","schema":{"type":"integer"}},{"name":"countries","in":"query","required":false,"description":"Count only signals whose linked lead is located in these countries. Comma-separated list of country names. Combined with `cities`. Only matches signals directly linked to a lead.","style":"form","explode":false,"schema":{"type":"array","items":{"type":"string"},"maxItems":100},"example":["France"]},{"name":"cities","in":"query","required":false,"description":"Count only signals whose linked lead is located in these cities. Comma-separated list of `name|country` pairs (each part URL-encoded), e.g. `Paris|France`.","schema":{"type":"string"},"example":"Paris|France"}],"responses":{"200":{"description":"Total number of matching signal detections.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2SignalCountResponse"},"examples":{"sample":{"summary":"Count result","value":{"total":42}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"403":{"$ref":"#/components/responses/V2Forbidden"},"404":{"description":"Returned when string company identifier(s) (`company_domain`, `company_linkedin_handle`, or `company_linkedin_url`) were supplied and none of them resolved to a known company in your workspace. Note: `company_id` is taken at face value and never triggers a `404` — an ID that does not belong to your workspace returns a zero count instead."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/workspace/signals/{id}":{"get":{"tags":["Signals"],"summary":"Get a single signal detection","description":"Returns one published signal detection by its ID.\n\n**Important:** the `id` path parameter is specific to your environment.\nStrict workspace scoping: a detection belonging to another workspace returns 404.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"ID of the detection (the `id` field from the list endpoint).","schema":{"type":"integer"}}],"responses":{"200":{"description":"Detection found","content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2SignalResponse"}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"403":{"$ref":"#/components/responses/V2Forbidden"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/company-mappings":{"get":{"tags":["Company Mapping"],"summary":"List company mappings","description":"Returns a paginated list of company mappings for the authenticated workspace.\n\nProfiles are not included in this response. Use `GET /v2/company-mappings/{mapping_id}` to retrieve a mapping with its enriched employee profiles.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","description":"Page number (starts at 1). Defaults to 1.","schema":{"type":"integer","minimum":1}},{"name":"page_size","in":"query","description":"Number of items per page. Defaults to 25. Maximum: 100.","schema":{"type":"integer","minimum":1,"maximum":100}}],"responses":{"200":{"description":"Paginated list of company mappings","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"35ms"}},"X-Total-Count":{"description":"Total number of mappings matching the query","schema":{"type":"integer","example":12}},"X-Page":{"description":"Current page number","schema":{"type":"integer","example":1}},"X-Page-Size":{"description":"Number of items per page","schema":{"type":"integer","example":25}},"X-Page-Count":{"description":"Total number of pages","schema":{"type":"integer","example":1}}},"content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id"],"properties":{"id":{"type":"integer","description":"Numeric SQL id of the company mapping"},"request_date":{"type":"string","format":"date-time","nullable":true,"description":"When the mapping was materialized"},"version":{"type":"integer","nullable":true,"description":"Mapping version (incremented on re-materialization)"},"status":{"type":"string","enum":["in_progress","complete"],"nullable":true,"description":"`in_progress` while the mapping is still being enriched; `complete` once all employee profiles have been resolved."},"company":{"type":"object","nullable":true,"required":["id"],"properties":{"id":{"type":"integer","description":"Numeric SQL id of the company"},"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true}}},"persona_id":{"type":"integer","nullable":true,"description":"Numeric id of the persona this mapping is attributed to. Null means the mapping applies to every persona (not attributed to one business line)."}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"$ref":"#/components/schemas/V2PaginationMeta"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"403":{"$ref":"#/components/responses/V2Forbidden"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/company-mappings/{mapping_id}":{"get":{"tags":["Company Mapping"],"summary":"Get a company mapping with profiles","description":"Returns a single company mapping for the authenticated workspace, including all enriched employee profiles.\n\nUse `mapping_id` as the path parameter, this is the mapping `id` returned as the top-level `id` of each item by `GET /v2/company-mappings`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"mapping_id","in":"path","required":true,"description":"The mapping's numeric SQL id (the integer returned as the list item's top-level `id`; not portable across environments, prod only)","schema":{"type":"integer","minimum":1}}],"responses":{"200":{"description":"Company mapping with enriched profiles","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"35ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["id","profiles"],"properties":{"id":{"type":"integer","description":"Numeric SQL id of the company mapping"},"request_date":{"type":"string","format":"date-time","nullable":true,"description":"When the mapping was materialized"},"version":{"type":"integer","nullable":true,"description":"Mapping version"},"status":{"type":"string","enum":["in_progress","complete"],"nullable":true,"description":"`in_progress` while the mapping is still being enriched; `complete` once all employee profiles have been resolved."},"company":{"type":"object","nullable":true,"required":["id"],"properties":{"id":{"type":"integer","description":"Numeric SQL id of the company"},"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true}}},"persona_id":{"type":"integer","nullable":true,"description":"Numeric id of the persona this mapping is attributed to. Null means the mapping applies to every persona (not attributed to one business line)."},"profiles":{"type":"array","description":"Enriched employee profiles for this company","items":{"type":"object","required":["id","position_start_date","seniority","department"],"properties":{"id":{"type":"integer"},"linkedin_handle":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"linkedin_about":{"type":"string","nullable":true},"position":{"type":"string","nullable":true},"position_start_date":{"type":"string","format":"date","nullable":true,"description":"Date the person started their current role, in ISO 8601 format (YYYY-MM-DD). Null when not available."},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"email":{"type":"string","nullable":true},"phone_number":{"type":"string","nullable":true},"linkedin_headline":{"type":"string","nullable":true},"location":{"type":"object","nullable":true,"properties":{"city":{"type":"string","nullable":true},"region":{"type":"string","nullable":true},"country":{"type":"string","nullable":true}},"description":"Location object with city, region, and country fields"},"seniority":{"type":"string","enum":["owner","founder","c_suite","partner","vp","head","director","manager","senior","entry","intern","unspecified"],"description":"This person's seniority level, based on their job title at this company. `unspecified` when the title does not give a clear seniority signal."},"department":{"type":"string","enum":["executive","board_investors","sales","marketing_communications","revenue_operations","customer_success","product_design","engineering","data_ai_analytics","it_security","rd_science","finance_accounting","legal_compliance","people_hr","business_operations","site_network_operations","supply_chain","manufacturing","procurement","quality_regulatory","strategy_corporate_development","consulting_delivery","other","unspecified"],"description":"This person's department, based on their job title at this company. `unspecified` when the title does not give a clear department signal."}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"403":{"$ref":"#/components/responses/V2Forbidden"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/companies/query":{"post":{"tags":["V2 Companies"],"summary":"Search companies by name or domain","description":"Searches the companies in your workspace by name and/or domain (case-insensitive substring) and returns the matches with their workspace company id.\n\nProvide at least one of `name` or `domain`. When both are given, only companies matching both are returned.\n\nUse the returned `id` directly as `company_ids` on `POST /v2/leads/query` to filter leads by company.\n\nAuthenticate with a `sk_live_` API key.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","anyOf":[{"required":["name"]},{"required":["domain"]}],"properties":{"name":{"type":"string","minLength":1,"maxLength":200,"description":"Case-insensitive substring to match against company names. At least one of `name` or `domain` is required.","example":"sales"},"domain":{"type":"string","minLength":1,"maxLength":200,"description":"Case-insensitive substring to match against company website domains. At least one of `name` or `domain` is required.","example":"salesforce.com"},"limit":{"type":"integer","minimum":1,"maximum":50,"description":"Maximum number of matches to return (default 20, max 50)."}}}}}},"responses":{"200":{"description":"Matching companies.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2CompanySearchResponse"},"examples":{"sample":{"summary":"Search result","value":{"data":[{"id":70030,"name":"Salesforce","domain":"salesforce.com","linkedin_handle":"salesforce"}]}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/companies/{id}":{"get":{"tags":["V2 Companies"],"summary":"Get a company","description":"Returns the enrichment data for a company in the authenticated workspace.\n\nThe `id` path parameter is a numeric identifier. Pass the `company_id` returned by other v2 endpoints.\n\nIf the company has not been enriched yet, the enrichment fields are returned as `null` — this endpoint never triggers enrichment.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"The company's numeric SQL id. Environment-specific, prod only, not portable across environments.","schema":{"type":"integer","minimum":1}}],"responses":{"200":{"description":"Company enrichment data","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"20ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"$ref":"#/components/schemas/V2CompanyDetail"}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/companies/{id}/pipeline-configs":{"patch":{"tags":["V2 Companies"],"summary":"Enable, update, or disable a company pipeline","description":"The single endpoint to turn account mapping and content generation on for this company, change how much runs, or turn it off again.\n\n`configuration` sets the depth: `account_mapping` runs account mapping only, `account_mapping_and_content` also generates content, and `disabled` turns both off. Calling this again for the same company updates the existing setting rather than creating a duplicate, so setting `configuration` back to `account_mapping` or `account_mapping_and_content` re-enables the pipeline.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"The company's ID in your workspace, as returned by other v2 endpoints.","schema":{"type":"integer","minimum":1}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["pipeline_type","configuration"],"properties":{"pipeline_type":{"type":"string","enum":["account_mapping_and_content"],"description":"Which pipeline to configure. Currently only `account_mapping_and_content` is supported."},"configuration":{"type":"string","enum":["account_mapping","account_mapping_and_content","disabled"],"description":"How much runs for this company: `account_mapping` (account mapping only), `account_mapping_and_content` (account mapping plus content), or `disabled` (turns the pipeline off)."}}},"examples":{"default":{"summary":"Enable the full cycle","value":{"pipeline_type":"account_mapping_and_content","configuration":"account_mapping_and_content"}},"disable":{"summary":"Disable the pipeline","value":{"pipeline_type":"account_mapping_and_content","configuration":"disabled"}}}}}},"responses":{"200":{"description":"Pipeline enabled, updated, or disabled","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["pipeline_type","configuration"],"properties":{"pipeline_type":{"type":"string","enum":["account_mapping_and_content"]},"configuration":{"type":"string","enum":["account_mapping","account_mapping_and_content","disabled"]}}}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/leads/{id}":{"get":{"tags":["V2 Leads"],"summary":"Get a lead","description":"Returns a lead in the authenticated workspace, with its linked profile details, a reference to its current company, and its LinkedIn work history.\n\nThe `id` path parameter is a numeric identifier. Pass the `lead_id` returned by other v2 endpoints, such as the signals endpoints.\n\nA lead with no linked profile is returned with the profile fields set to `null`. When the current company cannot be resolved, the `company` field is `null`. The `experiences` array lists the lead's work history in the order it appears on their LinkedIn profile, including their current position; it is `null` when this data is not available for this lead. None of these cases is an error.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"description":"The lead's numeric ID. Always use the `lead_id` returned by the signals endpoints — don't guess, hard-code, or copy an id from an example or another workspace.","schema":{"type":"integer","minimum":1}}],"responses":{"200":{"description":"Lead data","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"20ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"$ref":"#/components/schemas/V2LeadDetail"}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/leads/query":{"post":{"tags":["V2 Leads"],"summary":"Query workspace leads","description":"Returns the leads in your workspace, sorted by creation date (most recent first by default). Each item has the same shape as `GET /v2/leads/{id}`, plus its `created_at` date.\n\nThe list is cursor-paginated: each response includes `meta.next_cursor` — pass it back as `cursor` (with the same `sort` and filters) to fetch the next page, until `meta.has_more` is `false`.\n\nFilters are passed as a JSON body, so identifier arrays (`company_domain`, `company_linkedin_handle`, `company_linkedin_url`) are not bound by URL length limits. A company filter that matches no company in your workspace returns an empty page, not an error.\n\nAuthenticate with a `sk_live_` API key.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2LeadsQueryBody"}}}},"responses":{"200":{"description":"Cursor-paginated list of leads","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"35ms"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/V2LeadsPaginatedResponse"}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/enrich-company-mapping":{"post":{"tags":["Company Mapping"],"summary":"Enrich company mapping","description":"Resolves a company by domain, LinkedIn URL, LinkedIn handle, or company ID, then enriches the workspace company mapping asynchronously.\n\nReturns `202 Accepted` immediately. The enrichment runs in the background.\n\n---\n\n## Input\n\nProvide exactly one of `domain`, `linkedin_url`, `linkedin_handle` or `company_id`. Prefer `linkedin_url`, `linkedin_handle` or `company_id` when available; use `domain` only as a fallback.\n\n## Idempotency\n\nIf a recent enrichment already exists for the same company and workspace, the response reflects the existing request rather than creating a duplicate.\n\n## Personas\n\nA workspace can define several personas (ideal customer profile targeting criteria), each with its own locations and job titles. By default this call enriches the personas linked to the lists this company belongs to (every active persona when none of those lists names one, or when the company is on no list). Pass `persona_ids` to enrich specific personas instead — they run even if the company is not on their lists. Either way, the response `launches` array reports one entry per persona considered: `launched` (a new request was created and charged), `already_requested` (already enriched today for this company, at no extra cost), or skipped because the persona is missing a location or job titles (`skipped_no_location`, `skipped_no_job_titles`).\n\n## Credits\n\nCharges one credit for each persona actually launched. If your balance cannot cover every persona this call would launch, the whole call is refused and nothing is created or charged — a partial launch never happens. Additional credits are charged for each employee profile whose content is analyzed as enrichment continues. Returns `402` if your balance is insufficient, `422` if none of your personas can be mapped, or `422` if `persona_ids` names an id that is not one of your active personas.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"oneOf":[{"title":"Resolve by domain","type":"object","required":["domain"],"properties":{"domain":{"type":"string","description":"Company website domain (e.g. `acme.com`)","example":"acme.com"},"linkedin_url":{"type":"string","nullable":true,"description":"Optional LinkedIn company URL to disambiguate","example":"https://www.linkedin.com/company/acme"},"persona_ids":{"$ref":"#/components/schemas/EnrichPersonaIds"}}},{"title":"Resolve by LinkedIn URL","type":"object","required":["linkedin_url"],"properties":{"domain":{"type":"string","nullable":true,"description":"Optional company website domain","example":"acme.com"},"linkedin_url":{"type":"string","description":"LinkedIn company URL","example":"https://www.linkedin.com/company/acme"},"persona_ids":{"$ref":"#/components/schemas/EnrichPersonaIds"}}},{"title":"Resolve by LinkedIn handle","type":"object","required":["linkedin_handle"],"properties":{"linkedin_handle":{"type":"string","description":"LinkedIn company handle/slug (e.g. `acme`, the part after /company/)","example":"acme"},"persona_ids":{"$ref":"#/components/schemas/EnrichPersonaIds"}}},{"title":"Resolve by company_id","type":"object","required":["company_id"],"properties":{"company_id":{"type":"integer","description":"The company's ID in Sillage, if you already have it (e.g. from the company list or another v2 endpoint). This ID is specific to your environment. An unknown ID returns a 404.","example":789},"persona_ids":{"$ref":"#/components/schemas/EnrichPersonaIds"}}}]}}}},"responses":{"202":{"description":"Enrichment accepted","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-Response-Time":{"description":"Total server processing time","schema":{"type":"string","example":"45ms"}}},"content":{"application/json":{"schema":{"type":"object","required":["status","request_id","stage","launches"],"properties":{"status":{"type":"string","enum":["accepted"]},"request_id":{"type":"integer","deprecated":true,"description":"Numeric SQL id of the first launched (or, if none launched, first considered) persona's enrichment content request. Deprecated in favor of `launches[].request_id`, which reports every persona individually."},"stage":{"type":"string","description":"Processing stage of the enrichment request","enum":["account_mapping_in_progress"]},"launches":{"type":"array","description":"One entry per persona this call considered for your workspace.","items":{"$ref":"#/components/schemas/PersonaLaunch"}}}},"examples":{"accepted":{"summary":"Enrichment accepted, two personas launched","value":{"status":"accepted","request_id":12345,"stage":"account_mapping_in_progress","launches":[{"persona_id":501,"request_id":12345,"status":"launched","credits":1},{"persona_id":502,"request_id":12346,"status":"launched","credits":1}]}},"alreadyRequested":{"summary":"Same-day relaunch, already requested","value":{"status":"accepted","request_id":12345,"stage":"account_mapping_in_progress","launches":[{"persona_id":501,"request_id":12345,"status":"already_requested","credits":0},{"persona_id":502,"request_id":12346,"status":"already_requested","credits":0}]}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"402":{"$ref":"#/components/responses/V2PaymentRequired"},"403":{"$ref":"#/components/responses/V2Forbidden"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"$ref":"#/components/responses/V2Conflict"},"422":{"description":"Unprocessable entity. Either none of your personas can be mapped for this company — every persona is either missing or is missing a location or job titles, and the `launches` array reports each persona and why — or `persona_ids` names an id that is not one of your active personas.","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"oneOf":[{"$ref":"#/components/schemas/PersonaLaunchProblemDetails"},{"$ref":"#/components/schemas/ProblemDetails"}]},"examples":{"noPersonaLaunchable":{"summary":"No persona can be mapped","value":{"type":"https://docs.getsillage.com/errors/no-persona-launchable","title":"No persona can be mapped","status":422,"detail":"No persona in this workspace can be mapped — add a persona, or complete an existing persona location and job titles, then try again.","launches":[{"persona_id":501,"request_id":null,"status":"skipped_no_location","credits":0}]}},"invalidPersonaIds":{"summary":"persona_ids names an unknown persona","value":{"type":"https://docs.getsillage.com/errors/unprocessable-entity","title":"Unprocessable Entity","status":422,"detail":"persona_ids includes an id that is not one of your workspace’s active personas.","errors":{"persona_ids":["Unknown persona id: 999"]}}}}}}},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/agents":{"post":{"tags":["V2 Setup"],"deprecated":true,"summary":"Create agent","description":"Replaced by `/v3/signal-setups`: this endpoint stops answering on 1 April 2027.\n\nCreates an agent for the authenticated workspace.\n\nTen types are supported: `keyword_detection` (monitors LinkedIn posts for keywords,\nscoped to your target accounts), `keyword_post_search` (monitors LinkedIn posts for\nkeywords via a broad LinkedIn search, not scoped to your target accounts),\n`job_posting_keyword_detection` (monitors the job postings your tracked companies\npublish for keywords), five semantic watchlist types — `competitor`, `partner`,\n`customer` (company lists) and `influencer`, `champion` (profile lists) —\n`job_update` (detects job changes and promotions among the workspace’s contacts,\ntakes no parameters), and `champion_tracking` (detects when a tracked champion\nleaves their company, changes company, or is promoted).\n\nFor the five semantic watchlist types, a watchlist of the matching type is\n**implicitly created** and bound to the agent. `champion_tracking` works the same way,\nbut always binds a **profile watchlist of type `champion`** — the same list a `champion`\nagent can bind to, simultaneously. Pass `watchlist_id` to bind an existing list instead;\nits `type` must equal the expected watchlist type or the request returns 422.\n\nThe competitor arm additionally accepts an optional `parameters.mode`: `lead_discovery`\n(watches the competitor's team on LinkedIn from both directions — the people they\ncomment on or react to, wherever those people work, and the people who comment on or\nreact to the competitor team's own posts), `account_monitoring` (the\ndefault — only detects interactions between the competitor and your own top\naccounts, in both directions, no scraping), or `all` (both). No other agent type\naccepts `mode`.\n\nIt also accepts an optional `parameters.target_group`, independent of `mode`: it\npicks which people at the tracked competitor a lead-discovery run watches, and so\nwhose LinkedIn interactions it reads. `prospects` watches their new-business side\n(sales, account executives, SDR/BDR, revenue and exec leadership); `customers`\nwatches their account side (account management, customer success, support); `all`\n(the default when omitted) watches both.\n\n`competitor_activity` is not one of the ten types — it is a label that appears only\non individual signal detections (see the Signals endpoint), never as an agent's own\n`type`, and cannot be passed here. Nor can `content_engagement`: existing\ncontent-engagement agents keep it as their own type, but a `competitor` agent's\nlead discovery also reports it on individual signals without changing that\nagent's own `type`.\n\nThe agent is created **enabled** (`enabled: true`) and starts monitoring immediately.\n\nThe `keyword_post_search` and `competitor` arms additionally accept `schedule:\n{ \"cadence\": \"weekly\" }` to turn on a recurring weekly run at create — for the\ncompetitor arm this only takes effect when `parameters.mode` is `lead_discovery` or\n`all`, otherwise the request returns 422. Omit `schedule` to create the agent\nunscheduled.\n\n**Credits:** `champion_tracking` agents consume credits from your workspace balance each time a tracked champion is re-enriched, a recurring cost for as long as the agent stays enabled. Keyword agents (`keyword_detection`, `keyword_post_search`, `job_posting_keyword_detection`) consume credits for the keyword signals they detect.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"oneOf":[{"title":"keyword_detection","type":"object","required":["name","type","parameters"],"properties":{"tracking_keywords":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Keywords this agent looks for in LinkedIn posts. Minimum 1 required. A bare keyword matches broadly, including inside longer words and phrases, which finds more posts but adds noise. Wrap a keyword in double quotes (for example \"machine learning\") to match that exact phrase only, which cuts noise and sharpens precision."},"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["keyword_detection"]},"parameters":{"type":"object","required":["tracking_keywords"],"properties":{"tracking_keywords":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Keywords Sillage monitors on LinkedIn. Minimum 1 required."},"max_posts_to_scrape":{"type":"integer","minimum":1,"description":"Maximum number of posts to scrape per run."},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}}}},{"title":"keyword_post_search","type":"object","required":["name","type","parameters"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["keyword_post_search"]},"parameters":{"type":"object","required":["tracking_keywords"],"properties":{"tracking_keywords":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Keywords Sillage monitors on LinkedIn via a broad search. Minimum 1 required."},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},"schedule":{"type":"object","nullable":true,"required":["cadence"],"properties":{"cadence":{"type":"string","enum":["weekly"]}},"description":"Turn the agent's recurring weekly run on ({ \"cadence\": \"weekly\" }) or off (null). Only accepted on an agent whose response carries `schedulable: true` — sending it on a non-schedulable agent, or with a `cadence` other than \"weekly\", returns 422."}}},{"title":"competitor","type":"object","required":["name","type"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["competitor"]},"watchlist_id":{"type":"integer","description":"Optional. Bind to an existing competitor watchlist instead of creating a new one. The list type must equal \"competitor\" or the request returns 422."},"parameters":{"type":"object","description":"Optional configuration for this competitor agent.","properties":{"mode":{"type":"string","enum":["lead_discovery","account_monitoring","all"],"description":"What this agent does: `lead_discovery` watches the competitor's team on LinkedIn from both directions — the people they comment on or react to, wherever those people work, and the people who comment on or react to the competitor team's own posts; `account_monitoring` (default) only detects interactions between the competitor and your own top accounts, in both directions, no scraping; `all` does both. Defaults to `account_monitoring` when omitted."},"target_group":{"type":"string","enum":["prospects","customers","all"],"description":"Which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side: sales, account executives, SDR/BDR, revenue and exec leadership), `customers` (their account side: account management, customer success, support), or `all` (both). Defaults to `all` when omitted."}}},"schedule":{"type":"object","nullable":true,"required":["cadence"],"properties":{"cadence":{"type":"string","enum":["weekly"]}},"description":"Turn the weekly schedule on or off. Only accepted when `parameters.mode` (after this request) is `lead_discovery` or `all` — sent with `mode` left at (or defaulting to) `account_monitoring`, this returns 422."}}},{"title":"partner","type":"object","required":["name","type"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["partner"]},"watchlist_id":{"type":"integer","description":"Optional. Bind to an existing partner watchlist instead of creating a new one. The list type must equal \"partner\" or the request returns 422."}}},{"title":"customer","type":"object","required":["name","type"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["customer"]},"watchlist_id":{"type":"integer","description":"Optional. Bind to an existing customer watchlist instead of creating a new one. The list type must equal \"customer\" or the request returns 422."}}},{"title":"influencer","type":"object","required":["name","type"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["influencer"]},"watchlist_id":{"type":"integer","description":"Optional. Bind to an existing influencer watchlist instead of creating a new one. The list type must equal \"influencer\" or the request returns 422."}}},{"title":"champion","type":"object","required":["name","type"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["champion"]},"watchlist_id":{"type":"integer","description":"Optional. Bind to an existing champion watchlist instead of creating a new one. The list type must equal \"champion\" or the request returns 422."}}},{"title":"job_update","type":"object","required":["name","type"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["job_update"]}}},{"title":"job_posting_keyword_detection","type":"object","required":["name","type","parameters"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["job_posting_keyword_detection"]},"parameters":{"type":"object","required":["tracking_keywords"],"properties":{"tracking_keywords":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Keywords Sillage looks for in the job postings your tracked companies publish (title and description). Minimum 1 required."}}}}},{"title":"champion_tracking","type":"object","required":["name","type"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100,"description":"Display name of the agent."},"type":{"type":"string","enum":["champion_tracking"]},"watchlist_id":{"type":"integer","description":"Optional. Bind to an existing champion watchlist instead of creating a new one. The list type must equal \"champion\" or the request returns 422."}}}]}}}},"responses":{"201":{"description":"Agent created.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","name","type","enabled","parameters","watchlist_kind","watchlist_id","schedulable","schedule"],"properties":{"id":{"type":"integer","description":"Identifier of the agent."},"name":{"type":"string"},"type":{"type":"string","enum":["keyword_detection","keyword_post_search","job_update","job_posting","job_posting_keyword_detection","competitor_activity","content_engagement","influencer_engagement","champion_tracking","competitor","partner","customer","influencer","champion","unconfigured"],"description":"The agent type. Watchlist agents return their semantic type (competitor, partner, customer, influencer, champion). `unconfigured` marks an agent that still needs to be set up — either its watchlist has not been defined yet, or its watchlist was unbound; its `parameters` is empty and `watchlist_kind`/`watchlist_id` are null. Bind a watchlist to give it a type again. `competitor_activity` is a detection label only — it appears on individual signals, never as an agent's own type: it is not returned by this endpoint and cannot be passed when creating an agent. `content_engagement` is different: it remains a valid agent type for existing content-engagement agents, but it can also appear as a detection label on a `competitor` agent's signals — in that case the agent's own type stays `competitor`."},"enabled":{"type":"boolean","description":"Whether the agent is currently active."},"watchlist_kind":{"type":"string","enum":["company","profile"],"nullable":true,"description":"Kind of the bound watchlist, or null when unbound (paired with watchlist_id)."},"watchlist_id":{"type":"integer","nullable":true,"description":"The bound watchlist id, or null when the agent is unbound."},"schedulable":{"type":"boolean","description":"Whether this agent has a billed branch that can run on a schedule at all. `false` for every non-billed agent type and for a competitor agent whose `mode` is `account_monitoring` — the `schedule` field is then read-only null, and any write to it returns 422."},"schedule":{"type":"object","nullable":true,"required":["cadence"],"properties":{"cadence":{"type":"string","enum":["weekly"]}},"description":"The agent's weekly schedule, or null. Non-null only while `schedulable` is true and the schedule is currently active — `schedulable: true` with `schedule: null` means it can be scheduled but is not right now."},"parameters":{"oneOf":[{"title":"keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"keyword_post_search","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"job_posting_keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}}}},{"title":"job_update","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"seniority_levels":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"job_posting","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"search_strings":{"type":"array","items":{"type":"string"}},"job_locations":{"type":"array","items":{"type":"string"}},"published_at":{"type":"string"},"target_top_accounts_only":{"type":"boolean"}}},{"title":"competitor_activity","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"content_engagement","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"influencer_engagement","type":"object","properties":{"influencer_keywords":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"champion_tracking","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"competitor","type":"object","description":"Competitor watchlist agent. Optional `mode` selects what it does: `lead_discovery` watches the competitor's team on LinkedIn from both directions — the people they comment on or react to, wherever those people work, and the people who comment on or react to the competitor team's own posts; `account_monitoring` (the default when absent) only detects interactions between the competitor and your own top accounts, in both directions, with no scraping; `all` does both. `target_group` selects which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side), `customers` (their account side), or `all` (the default when absent — both).","properties":{"mode":{"type":"string","enum":["lead_discovery","account_monitoring","all"],"description":"What this competitor agent does. Defaults to `account_monitoring` when omitted."},"target_group":{"type":"string","enum":["prospects","customers","all"],"nullable":true,"description":"Which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side: sales, account executives, SDR/BDR, revenue and exec leadership), `customers` (their account side: account management, customer success, support), or `all` (both). Reads back as `all` when never set."},"resolved_target_persona":{"type":"array","items":{"type":"string"},"description":"The exact job titles the agent's next discovery run searches for — derived from `target_group`, or from the carried-over list while `target_group` is `null`."}}},{"title":"partner","type":"object","description":"Partner watchlist agent, no keyword parameters."},{"title":"customer","type":"object","description":"Customer watchlist agent, no keyword parameters."},{"title":"influencer","type":"object","description":"Influencer watchlist agent, no keyword parameters."},{"title":"champion","type":"object","description":"Champion watchlist agent, no keyword parameters."}]},"created_at":{"type":"string","format":"date-time"},"updated_at":{"type":"string","format":"date-time"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Invalid request body, unsupported `type`, missing `tracking_keywords` for\n`keyword_detection` or `keyword_post_search`, or `watchlist_id` references a list\nwhose type does not match the expected watchlist type for the chosen agent type.\n\nAlso returned when `schedule.cadence` is anything other than `\"weekly\"`, or when\n`schedule` is sent on a competitor agent whose `parameters.mode` (after this\nrequest) is not `lead_discovery` or `all` — no schedule is created in that case.\n\nAlso returned for every type except `job_update`, `job_posting_keyword_detection`,\nand `champion_tracking` when the workspace is not set up yet. These setup\nrejections carry a dedicated `type` so they can be told apart programmatically —\n`https://docs.getsillage.com/errors/persona-incomplete` (no persona, or persona\nmissing `job_title`/`location`) or\n`https://docs.getsillage.com/errors/insufficient-top-accounts` (zero top\naccounts) — and the `detail` names the exact prerequisite to fix before\nretrying. When both fail, the persona-incomplete `type` is returned and the\n`detail` names both.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"},"example":{"type":"https://docs.getsillage.com/errors/persona-incomplete","title":"Persona incomplete","status":422,"detail":"Create a persona with sillage_v2_upsert_persona (job_title and location required) before creating an agent."}}}},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"get":{"tags":["V2 Setup"],"deprecated":true,"summary":"List agents","description":"Replaced by `/v3/signal-setups`: this endpoint stops answering on 1 April 2027.\n\nReturns a paginated list of your agents — keyword detection, job-posting keyword detection, job-change tracking, and watchlist monitors.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number (starts at 1). Defaults to 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":25,"default":10},"description":"Number of agents per page. Defaults to 10, max 25."}],"responses":{"200":{"description":"Paginated list of agents.","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id","name","type","enabled","parameters","watchlist_kind","watchlist_id","schedulable","schedule"],"properties":{"id":{"type":"integer","description":"Identifier of the agent."},"name":{"type":"string"},"type":{"type":"string","enum":["keyword_detection","keyword_post_search","job_update","job_posting","job_posting_keyword_detection","competitor_activity","content_engagement","influencer_engagement","champion_tracking","competitor","partner","customer","influencer","champion","unconfigured"],"description":"The agent type. Watchlist agents return their semantic type (competitor, partner, customer, influencer, champion). `unconfigured` marks an agent that still needs to be set up — either its watchlist has not been defined yet, or its watchlist was unbound; its `parameters` is empty and `watchlist_kind`/`watchlist_id` are null. Bind a watchlist to give it a type again. `competitor_activity` is a detection label only — it appears on individual signals, never as an agent's own type: it is not returned by this endpoint and cannot be passed when creating an agent. `content_engagement` is different: it remains a valid agent type for existing content-engagement agents, but it can also appear as a detection label on a `competitor` agent's signals — in that case the agent's own type stays `competitor`."},"enabled":{"type":"boolean","description":"Whether the agent is currently active."},"watchlist_kind":{"type":"string","enum":["company","profile"],"nullable":true,"description":"Kind of the bound watchlist, or null when unbound (paired with watchlist_id)."},"watchlist_id":{"type":"integer","nullable":true,"description":"The bound watchlist id, or null when the agent is unbound."},"schedulable":{"type":"boolean","description":"Whether this agent has a billed branch that can run on a schedule at all. `false` for every non-billed agent type and for a competitor agent whose `mode` is `account_monitoring` — the `schedule` field is then read-only null, and any write to it returns 422."},"schedule":{"type":"object","nullable":true,"required":["cadence"],"properties":{"cadence":{"type":"string","enum":["weekly"]}},"description":"The agent's weekly schedule, or null. Non-null only while `schedulable` is true and the schedule is currently active — `schedulable: true` with `schedule: null` means it can be scheduled but is not right now."},"parameters":{"oneOf":[{"title":"keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"keyword_post_search","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"job_posting_keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}}}},{"title":"job_update","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"seniority_levels":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"job_posting","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"search_strings":{"type":"array","items":{"type":"string"}},"job_locations":{"type":"array","items":{"type":"string"}},"published_at":{"type":"string"},"target_top_accounts_only":{"type":"boolean"}}},{"title":"competitor_activity","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"content_engagement","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"influencer_engagement","type":"object","properties":{"influencer_keywords":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"champion_tracking","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"competitor","type":"object","description":"Competitor watchlist agent. Optional `mode` selects what it does: `lead_discovery` watches the competitor's team on LinkedIn from both directions — the people they comment on or react to, wherever those people work, and the people who comment on or react to the competitor team's own posts; `account_monitoring` (the default when absent) only detects interactions between the competitor and your own top accounts, in both directions, with no scraping; `all` does both. `target_group` selects which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side), `customers` (their account side), or `all` (the default when absent — both).","properties":{"mode":{"type":"string","enum":["lead_discovery","account_monitoring","all"],"description":"What this competitor agent does. Defaults to `account_monitoring` when omitted."},"target_group":{"type":"string","enum":["prospects","customers","all"],"nullable":true,"description":"Which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side: sales, account executives, SDR/BDR, revenue and exec leadership), `customers` (their account side: account management, customer success, support), or `all` (both). Reads back as `all` when never set."},"resolved_target_persona":{"type":"array","items":{"type":"string"},"description":"The exact job titles the agent's next discovery run searches for — derived from `target_group`, or from the carried-over list while `target_group` is `null`."}}},{"title":"partner","type":"object","description":"Partner watchlist agent, no keyword parameters."},{"title":"customer","type":"object","description":"Customer watchlist agent, no keyword parameters."},{"title":"influencer","type":"object","description":"Influencer watchlist agent, no keyword parameters."},{"title":"champion","type":"object","description":"Champion watchlist agent, no keyword parameters."}]},"created_at":{"type":"string","format":"date-time"},"updated_at":{"type":"string","format":"date-time"}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer"},"page_size":{"type":"integer"},"page_count":{"type":"integer"},"total":{"type":"integer"}}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Invalid `page` or `page_size` query parameter."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/agents/{agent_id}":{"get":{"tags":["V2 Setup"],"deprecated":true,"summary":"Get agent","description":"Replaced by `/v3/signal-setups`: this endpoint stops answering on 1 April 2027.\n\nReturns a single agent by its numeric id, scoped to the authenticated workspace.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the agent."}],"responses":{"200":{"description":"Agent found.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","name","type","enabled","parameters","watchlist_kind","watchlist_id","schedulable","schedule"],"properties":{"id":{"type":"integer","description":"Identifier of the agent."},"name":{"type":"string"},"type":{"type":"string","enum":["keyword_detection","keyword_post_search","job_update","job_posting","job_posting_keyword_detection","competitor_activity","content_engagement","influencer_engagement","champion_tracking","competitor","partner","customer","influencer","champion","unconfigured"],"description":"The agent type. Watchlist agents return their semantic type (competitor, partner, customer, influencer, champion). `unconfigured` marks an agent that still needs to be set up — either its watchlist has not been defined yet, or its watchlist was unbound; its `parameters` is empty and `watchlist_kind`/`watchlist_id` are null. Bind a watchlist to give it a type again. `competitor_activity` is a detection label only — it appears on individual signals, never as an agent's own type: it is not returned by this endpoint and cannot be passed when creating an agent. `content_engagement` is different: it remains a valid agent type for existing content-engagement agents, but it can also appear as a detection label on a `competitor` agent's signals — in that case the agent's own type stays `competitor`."},"enabled":{"type":"boolean","description":"Whether the agent is currently active."},"watchlist_kind":{"type":"string","enum":["company","profile"],"nullable":true,"description":"Kind of the bound watchlist, or null when unbound (paired with watchlist_id)."},"watchlist_id":{"type":"integer","nullable":true,"description":"The bound watchlist id, or null when the agent is unbound."},"schedulable":{"type":"boolean","description":"Whether this agent has a billed branch that can run on a schedule at all. `false` for every non-billed agent type and for a competitor agent whose `mode` is `account_monitoring` — the `schedule` field is then read-only null, and any write to it returns 422."},"schedule":{"type":"object","nullable":true,"required":["cadence"],"properties":{"cadence":{"type":"string","enum":["weekly"]}},"description":"The agent's weekly schedule, or null. Non-null only while `schedulable` is true and the schedule is currently active — `schedulable: true` with `schedule: null` means it can be scheduled but is not right now."},"parameters":{"oneOf":[{"title":"keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"keyword_post_search","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"job_posting_keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}}}},{"title":"job_update","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"seniority_levels":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"job_posting","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"search_strings":{"type":"array","items":{"type":"string"}},"job_locations":{"type":"array","items":{"type":"string"}},"published_at":{"type":"string"},"target_top_accounts_only":{"type":"boolean"}}},{"title":"competitor_activity","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"content_engagement","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"influencer_engagement","type":"object","properties":{"influencer_keywords":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"champion_tracking","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"competitor","type":"object","description":"Competitor watchlist agent. Optional `mode` selects what it does: `lead_discovery` watches the competitor's team on LinkedIn from both directions — the people they comment on or react to, wherever those people work, and the people who comment on or react to the competitor team's own posts; `account_monitoring` (the default when absent) only detects interactions between the competitor and your own top accounts, in both directions, with no scraping; `all` does both. `target_group` selects which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side), `customers` (their account side), or `all` (the default when absent — both).","properties":{"mode":{"type":"string","enum":["lead_discovery","account_monitoring","all"],"description":"What this competitor agent does. Defaults to `account_monitoring` when omitted."},"target_group":{"type":"string","enum":["prospects","customers","all"],"nullable":true,"description":"Which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side: sales, account executives, SDR/BDR, revenue and exec leadership), `customers` (their account side: account management, customer success, support), or `all` (both). Reads back as `all` when never set."},"resolved_target_persona":{"type":"array","items":{"type":"string"},"description":"The exact job titles the agent's next discovery run searches for — derived from `target_group`, or from the carried-over list while `target_group` is `null`."}}},{"title":"partner","type":"object","description":"Partner watchlist agent, no keyword parameters."},{"title":"customer","type":"object","description":"Customer watchlist agent, no keyword parameters."},{"title":"influencer","type":"object","description":"Influencer watchlist agent, no keyword parameters."},{"title":"champion","type":"object","description":"Champion watchlist agent, no keyword parameters."}]},"created_at":{"type":"string","format":"date-time"},"updated_at":{"type":"string","format":"date-time"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `agent_id`, must be a positive integer."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"put":{"tags":["V2 Setup"],"deprecated":true,"summary":"Update agent","description":"Replaced by `/v3/signal-setups`: this endpoint stops answering on 1 April 2027.\n\nPartially updates an agent. All fields are optional, send only the ones to change.\n\nChanging `parameters` creates a new immutable campaign-setting version\nand repoints the agent to it. Changing only `name` or `enabled` mutates the agent\nrow directly without creating a new version.\n\n`parameters` takes either `tracking_keywords` (with an optional `start_date`), or\n`mode` and/or `target_group`, never mixed with the keyword fields. Both apply to\ncompetitor agents only: `mode` changes what the agent does, `target_group` changes\nwhich people at the tracked competitor a lead-discovery run watches. Sending just\none leaves the other unchanged.\n\n`schedule` is top-level, not inside `parameters`: send `{ \"cadence\": \"weekly\" }`\nto turn the agent's recurring weekly run on, or `null` to turn it off. Only\naccepted when the agent (after this request) has a billed branch to schedule —\ncheck `schedulable` on a GET first.\n\nA signal setup cannot be updated here: use `PATCH /v3/signal-setups/{id}`\nwith the same id.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the agent"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","minProperties":1,"properties":{"name":{"type":"string","minLength":1,"maxLength":100},"enabled":{"type":"boolean","description":"Enable or disable the agent."},"parameters":{"type":"object","minProperties":1,"properties":{"tracking_keywords":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Keywords this agent looks for in LinkedIn posts. Minimum 1 required. A bare keyword matches broadly, including inside longer words and phrases, which finds more posts but adds noise. Wrap a keyword in double quotes (for example \"machine learning\") to match that exact phrase only, which cuts noise and sharpens precision."},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."},"mode":{"type":"string","enum":["lead_discovery","account_monitoring","all"],"description":"Competitor agents only. What the agent does: `lead_discovery` watches the competitor's team on LinkedIn from both directions — the people they comment on or react to, wherever those people work, and the people who comment on or react to the competitor team's own posts; `account_monitoring` only detects interactions between the competitor and your own top accounts, in both directions, with no scraping; `all` does both. Send it alone or together with `target_group`, without `tracking_keywords` or `start_date`. Sending it for any other agent type returns 422."},"target_group":{"type":"string","enum":["prospects","customers","all"],"description":"Competitor agents only. Which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side: sales, account executives, SDR/BDR, revenue and exec leadership), `customers` (their account side: account management, customer success, support), or `all` (both). Send it alone or together with `mode`, without `tracking_keywords` or `start_date`. Sending it for any other agent type returns 422."}}},"watchlist_kind":{"type":"string","enum":["company","profile"],"nullable":true,"description":"Optional. Kind of the watchlist to bind. Derived from the agent type when omitted alongside watchlist_id. Providing a kind that contradicts the agent type returns 422. Null (alongside null watchlist_id) to unbind."},"watchlist_id":{"type":"integer","nullable":true,"description":"Bind the agent to a watchlist. watchlist_kind is optional, the kind is derived from the agent type when omitted. Null (both fields null) to unbind."},"schedule":{"type":"object","nullable":true,"required":["cadence"],"properties":{"cadence":{"type":"string","enum":["weekly"]}},"description":"Turn the agent's recurring weekly run on ({ \"cadence\": \"weekly\" }) or off (null). Only accepted on an agent whose response carries `schedulable: true` — sending it on a non-schedulable agent, or with a `cadence` other than \"weekly\", returns 422."}}}}}},"responses":{"200":{"description":"Agent updated.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","name","type","enabled","parameters","watchlist_kind","watchlist_id","schedulable","schedule"],"properties":{"id":{"type":"integer","description":"Identifier of the agent."},"name":{"type":"string"},"type":{"type":"string","enum":["keyword_detection","keyword_post_search","job_update","job_posting","job_posting_keyword_detection","competitor_activity","content_engagement","influencer_engagement","champion_tracking","competitor","partner","customer","influencer","champion","unconfigured"],"description":"The agent type. Watchlist agents return their semantic type (competitor, partner, customer, influencer, champion). `unconfigured` marks an agent that still needs to be set up — either its watchlist has not been defined yet, or its watchlist was unbound; its `parameters` is empty and `watchlist_kind`/`watchlist_id` are null. Bind a watchlist to give it a type again. `competitor_activity` is a detection label only — it appears on individual signals, never as an agent's own type: it is not returned by this endpoint and cannot be passed when creating an agent. `content_engagement` is different: it remains a valid agent type for existing content-engagement agents, but it can also appear as a detection label on a `competitor` agent's signals — in that case the agent's own type stays `competitor`."},"enabled":{"type":"boolean","description":"Whether the agent is currently active."},"watchlist_kind":{"type":"string","enum":["company","profile"],"nullable":true,"description":"Kind of the bound watchlist, or null when unbound (paired with watchlist_id)."},"watchlist_id":{"type":"integer","nullable":true,"description":"The bound watchlist id, or null when the agent is unbound."},"schedulable":{"type":"boolean","description":"Whether this agent has a billed branch that can run on a schedule at all. `false` for every non-billed agent type and for a competitor agent whose `mode` is `account_monitoring` — the `schedule` field is then read-only null, and any write to it returns 422."},"schedule":{"type":"object","nullable":true,"required":["cadence"],"properties":{"cadence":{"type":"string","enum":["weekly"]}},"description":"The agent's weekly schedule, or null. Non-null only while `schedulable` is true and the schedule is currently active — `schedulable: true` with `schedule: null` means it can be scheduled but is not right now."},"parameters":{"oneOf":[{"title":"keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"keyword_post_search","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}},"start_date":{"type":"string","description":"ISO 8601 date, scrape only posts published after this date."}}},{"title":"job_posting_keyword_detection","type":"object","properties":{"tracking_keywords":{"type":"array","items":{"type":"string"}}}},{"title":"job_update","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"seniority_levels":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"job_posting","type":"object","properties":{"job_titles":{"type":"array","items":{"type":"string"}},"search_strings":{"type":"array","items":{"type":"string"}},"job_locations":{"type":"array","items":{"type":"string"}},"published_at":{"type":"string"},"target_top_accounts_only":{"type":"boolean"}}},{"title":"competitor_activity","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"content_engagement","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"influencer_engagement","type":"object","properties":{"influencer_keywords":{"type":"array","items":{"type":"string"}},"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"champion_tracking","type":"object","properties":{"company_domains_to_scrape":{"type":"array","items":{"type":"string"}},"target_persona":{"type":"array","items":{"type":"string"}},"target_persona_locations":{"type":"array","items":{"type":"string"}},"interested_by":{"type":"object","properties":{"prospects":{"type":"boolean"},"customers":{"type":"boolean"}}},"keywords_for_social_detection":{"type":"array","items":{"type":"string"}},"author_roles":{"type":"array","items":{"type":"string"}},"author_industries":{"type":"array","items":{"type":"string"}},"target_linkedin_profiles":{"type":"array","items":{"type":"string"}}}},{"title":"competitor","type":"object","description":"Competitor watchlist agent. Optional `mode` selects what it does: `lead_discovery` watches the competitor's team on LinkedIn from both directions — the people they comment on or react to, wherever those people work, and the people who comment on or react to the competitor team's own posts; `account_monitoring` (the default when absent) only detects interactions between the competitor and your own top accounts, in both directions, with no scraping; `all` does both. `target_group` selects which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side), `customers` (their account side), or `all` (the default when absent — both).","properties":{"mode":{"type":"string","enum":["lead_discovery","account_monitoring","all"],"description":"What this competitor agent does. Defaults to `account_monitoring` when omitted."},"target_group":{"type":"string","enum":["prospects","customers","all"],"nullable":true,"description":"Which people at the tracked competitor a lead-discovery run watches: `prospects` (their new-business side: sales, account executives, SDR/BDR, revenue and exec leadership), `customers` (their account side: account management, customer success, support), or `all` (both). Reads back as `all` when never set."},"resolved_target_persona":{"type":"array","items":{"type":"string"},"description":"The exact job titles the agent's next discovery run searches for — derived from `target_group`, or from the carried-over list while `target_group` is `null`."}}},{"title":"partner","type":"object","description":"Partner watchlist agent, no keyword parameters."},{"title":"customer","type":"object","description":"Customer watchlist agent, no keyword parameters."},{"title":"influencer","type":"object","description":"Influencer watchlist agent, no keyword parameters."},{"title":"champion","type":"object","description":"Champion watchlist agent, no keyword parameters."}]},"created_at":{"type":"string","format":"date-time"},"updated_at":{"type":"string","format":"date-time"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"This is a signal setup. Update it with `PATCH /v3/signal-setups/{id}`."},"422":{"description":"Invalid request body or `agent_id`, empty body, `tracking_keywords` below minimum, `parameters` mixing `tracking_keywords`/`start_date` with `mode`/`target_group`, `mode` or `target_group` on an agent that is not a competitor, `schedule.cadence` other than `\"weekly\"`, a `schedule` write on an agent whose `schedulable` (after this request) is `false` — no schedule is created or changed in that case — or `enabled: false` combined with a non-null `schedule` in the same request."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"delete":{"tags":["V2 Setup"],"deprecated":true,"summary":"Delete agent","description":"Replaced by `/v3/signal-setups`: this endpoint stops answering on 1 April 2027.\n\nSoft-deletes an agent. The agent is archived (`deleted_at` set, `enabled` set to false)\nand no longer returned by the list or get endpoints.\n\nSignal and detection data linked to the agent is preserved.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the agent"}],"responses":{"200":{"description":"Agent deleted.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id"],"properties":{"id":{"type":"integer","description":"Identifier of the deleted agent."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `agent_id`, must be a positive integer."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/lists":{"post":{"tags":["V2 Lists"],"summary":"Create list","description":"Creates a reusable, workspace-scoped list of companies or people. Whether it holds companies or people is derived from the immutable `type`.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["type","name"],"properties":{"type":{"type":"string","enum":["competitor","partner","customer","prospect","influencer","champion","employee"],"description":"Immutable; determines whether the list holds companies or people."},"name":{"type":"string","minLength":1},"description":{"type":"string"},"default_tracking_status":{"type":"string","enum":["followed","unfollowed"],"description":"What happens to a member of this list by default. Defaults to `followed` when omitted."},"tier":{"type":"integer","nullable":true,"minimum":1,"maximum":3,"description":"Only allowed on a `customer` or `prospect` list — sending it on any other type is rejected with a 400. Set once at creation and never changeable afterwards: create a new list instead of re-tiering this one, since a tier change would silently re-tier every member already on it."},"persona_ids":{"type":"array","items":{"type":"integer"},"description":"The personas this list belongs to. Omit, or send an empty array, to create a list that applies to every persona."}}}}}},"responses":{"201":{"description":"The created list.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","kind","type","name"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the list."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","prospect","influencer","champion","employee"],"description":"Immutable list type. competitor/partner/customer/prospect → a list of companies; influencer/champion/employee → a list of people. `employee` is the workspace's own \"All my employees\" list: it is created for you and cannot be created through the API."},"name":{"type":"string","description":"Name of the list."},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"member_count":{"type":"integer","description":"How many companies or people are on the list. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents reading this list. Omitted in `concise`."},"tier":{"type":"integer","nullable":true,"description":"Tier of the list, for customer and prospect lists only. Null on every other type. Omitted in `concise`."},"default_tracking_status":{"type":"string","enum":["followed","unfollowed"],"description":"What a member of this list gets when it joins. An unfollowed account is not scraped for new signals and does not consume credits. Each member can be changed individually afterwards. Omitted in `concise`."},"default_signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"description":"Default signal bucket of the list, overridable per member. Recorded and returned only — it changes no behaviour today. Omitted in `concise`."},"archived_at":{"type":"string","format":"date-time","nullable":true,"description":"When the list was archived, or null while it is in use. An archived list keeps every member, but drops out of `GET /v2/lists` unless you ask for it. Omitted in `concise`."},"persona_ids":{"type":"array","items":{"type":"integer"},"description":"The personas this list belongs to. An empty array means the list applies to every persona. Omitted in `concise`."}}}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Invalid request body, or one of `persona_ids` does not belong to this workspace."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"get":{"tags":["V2 Lists"],"summary":"List lists","description":"Returns a paginated list of the workspace's lists. The total is in `meta.pagination`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number (starts at 1). Defaults to 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":25},"description":"Items per page. Defaults to 25, max 100."},{"name":"type","in":"query","required":false,"schema":{"type":"string","enum":["competitor","partner","customer","prospect","influencer","champion","employee"]},"description":"Filter by list type."},{"name":"include_archived","in":"query","required":false,"schema":{"type":"string","enum":["true","false"]},"description":"Set to `true` to get archived lists alongside the active ones. Archived lists are left out by default, and deleted lists never appear."},{"name":"persona_id","in":"query","required":false,"schema":{"type":"integer"},"description":"Filter to one persona. Returns the lists that belong to it, plus every list that belongs to no persona. Omit to get every list in the workspace. This id is specific to your environment."},{"name":"response_format","in":"query","required":false,"schema":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized"},"description":"Verbosity: `concise` (id/kind/type/name only), `normalized` (default, adds description, counts and the list defaults), `detailed` (identical to normalized; lists carry no heavy payload). A `concise` list is exactly `{ id, kind, type, name }` — every other field documented below is absent from it, not null."}],"responses":{"200":{"description":"Paginated lists.","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id","kind","type","name"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the list."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","prospect","influencer","champion","employee"],"description":"Immutable list type. competitor/partner/customer/prospect → a list of companies; influencer/champion/employee → a list of people. `employee` is the workspace's own \"All my employees\" list: it is created for you and cannot be created through the API."},"name":{"type":"string","description":"Name of the list."},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"member_count":{"type":"integer","description":"How many companies or people are on the list. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents reading this list. Omitted in `concise`."},"tier":{"type":"integer","nullable":true,"description":"Tier of the list, for customer and prospect lists only. Null on every other type. Omitted in `concise`."},"default_tracking_status":{"type":"string","enum":["followed","unfollowed"],"description":"What a member of this list gets when it joins. An unfollowed account is not scraped for new signals and does not consume credits. Each member can be changed individually afterwards. Omitted in `concise`."},"default_signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"description":"Default signal bucket of the list, overridable per member. Recorded and returned only — it changes no behaviour today. Omitted in `concise`."},"archived_at":{"type":"string","format":"date-time","nullable":true,"description":"When the list was archived, or null while it is in use. An archived list keeps every member, but drops out of `GET /v2/lists` unless you ask for it. Omitted in `concise`."},"persona_ids":{"type":"array","items":{"type":"integer"},"description":"The personas this list belongs to. An empty array means the list applies to every persona. Omitted in `concise`."}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer"},"page_size":{"type":"integer"},"page_count":{"type":"integer"},"total":{"type":"integer"}}}}}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Invalid query parameters, or `persona_id` does not belong to this workspace."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/lists/{kind}/{list_id}":{"get":{"tags":["V2 Lists"],"summary":"Get list","description":"Fetches one list by its numeric id.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."},{"name":"response_format","in":"query","required":false,"schema":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized"},"description":"Verbosity: `concise` (id/kind/type/name only), `normalized` (default, adds description, counts and the list defaults), `detailed` (identical to normalized; lists carry no heavy payload). A `concise` list is exactly `{ id, kind, type, name }` — every other field documented below is absent from it, not null."}],"responses":{"200":{"description":"The list.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","kind","type","name"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the list."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","prospect","influencer","champion","employee"],"description":"Immutable list type. competitor/partner/customer/prospect → a list of companies; influencer/champion/employee → a list of people. `employee` is the workspace's own \"All my employees\" list: it is created for you and cannot be created through the API."},"name":{"type":"string","description":"Name of the list."},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"member_count":{"type":"integer","description":"How many companies or people are on the list. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents reading this list. Omitted in `concise`."},"tier":{"type":"integer","nullable":true,"description":"Tier of the list, for customer and prospect lists only. Null on every other type. Omitted in `concise`."},"default_tracking_status":{"type":"string","enum":["followed","unfollowed"],"description":"What a member of this list gets when it joins. An unfollowed account is not scraped for new signals and does not consume credits. Each member can be changed individually afterwards. Omitted in `concise`."},"default_signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"description":"Default signal bucket of the list, overridable per member. Recorded and returned only — it changes no behaviour today. Omitted in `concise`."},"archived_at":{"type":"string","format":"date-time","nullable":true,"description":"When the list was archived, or null while it is in use. An archived list keeps every member, but drops out of `GET /v2/lists` unless you ask for it. Omitted in `concise`."},"persona_ids":{"type":"array","items":{"type":"integer"},"description":"The personas this list belongs to. An empty array means the list applies to every persona. Omitted in `concise`."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `list_id`."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"put":{"tags":["V2 Lists"],"summary":"Update list","description":"Updates a list's name, description or default tracking status, archives or unarchives it, and replaces which personas it belongs to. The `type` is immutable. Every workspace starts with three default lists, Tier 1/2/3 — they can be renamed like any other list, but archiving one fails with 409.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","description":"`type` is immutable and is ignored if provided.","properties":{"name":{"type":"string","minLength":1},"description":{"type":"string","nullable":true,"description":"Pass null to clear."},"default_tracking_status":{"type":"string","enum":["followed","unfollowed"],"description":"Changes the default given to members added from now on. Members already on the list keep the status they carry."},"archived":{"type":"boolean","description":"Set to `true` to archive the list, `false` to bring it back. Archiving keeps every member; the list just leaves your default listing. Omit to leave it as it is."},"persona_ids":{"type":"array","items":{"type":"integer"},"description":"Replaces the full set of personas this list belongs to. Omit to leave them untouched; send an empty array to make the list apply to every persona."}}}}}},"responses":{"200":{"description":"The updated list.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","kind","type","name"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the list."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","prospect","influencer","champion","employee"],"description":"Immutable list type. competitor/partner/customer/prospect → a list of companies; influencer/champion/employee → a list of people. `employee` is the workspace's own \"All my employees\" list: it is created for you and cannot be created through the API."},"name":{"type":"string","description":"Name of the list."},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"member_count":{"type":"integer","description":"How many companies or people are on the list. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents reading this list. Omitted in `concise`."},"tier":{"type":"integer","nullable":true,"description":"Tier of the list, for customer and prospect lists only. Null on every other type. Omitted in `concise`."},"default_tracking_status":{"type":"string","enum":["followed","unfollowed"],"description":"What a member of this list gets when it joins. An unfollowed account is not scraped for new signals and does not consume credits. Each member can be changed individually afterwards. Omitted in `concise`."},"default_signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"description":"Default signal bucket of the list, overridable per member. Recorded and returned only — it changes no behaviour today. Omitted in `concise`."},"archived_at":{"type":"string","format":"date-time","nullable":true,"description":"When the list was archived, or null while it is in use. An archived list keeps every member, but drops out of `GET /v2/lists` unless you ask for it. Omitted in `concise`."},"persona_ids":{"type":"array","items":{"type":"integer"},"description":"The personas this list belongs to. An empty array means the list applies to every persona. Omitted in `concise`."}}}}}}}},"400":{"$ref":"#/components/responses/V2BadRequest"},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"The request tries to archive one of the default Tier 1/2/3 lists or the \"All my employees\" list every workspace starts with, or to move the employee list to a business unit; those cannot be done."},"422":{"description":"Invalid `list_id` or request body, or one of `persona_ids` does not belong to this workspace."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"delete":{"tags":["V2 Lists"],"summary":"Delete list","description":"Deletes a list. The list and its members stop being returned by every endpoint, but nothing is destroyed: call `POST /v2/lists/{kind}/{list_id}/restore` to bring it back exactly as it was. Fails with 409 if one or more agents still read it, or if the list is one of the three default Tier 1/2/3 lists every workspace starts with — those cannot be deleted. To take a list out of the way without deleting it, archive it instead with `PUT /v2/lists/{kind}/{list_id}`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."}],"responses":{"200":{"description":"The deleted list id.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id"],"properties":{"id":{"type":"integer"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"One or more agents still read this list, or it is one of the default Tier 1/2/3 lists or the \"All my employees\" list every workspace starts with — those cannot be deleted."},"422":{"description":"Invalid `list_id`."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/lists/{kind}/{list_id}/restore":{"post":{"tags":["V2 Lists"],"summary":"Restore list","description":"Brings a deleted list back, with the same members and settings it had. Calling this on a list that was never deleted changes nothing and still succeeds.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."}],"responses":{"200":{"description":"The restored list.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","kind","type","name"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the list."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","prospect","influencer","champion","employee"],"description":"Immutable list type. competitor/partner/customer/prospect → a list of companies; influencer/champion/employee → a list of people. `employee` is the workspace's own \"All my employees\" list: it is created for you and cannot be created through the API."},"name":{"type":"string","description":"Name of the list."},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"member_count":{"type":"integer","description":"How many companies or people are on the list. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents reading this list. Omitted in `concise`."},"tier":{"type":"integer","nullable":true,"description":"Tier of the list, for customer and prospect lists only. Null on every other type. Omitted in `concise`."},"default_tracking_status":{"type":"string","enum":["followed","unfollowed"],"description":"What a member of this list gets when it joins. An unfollowed account is not scraped for new signals and does not consume credits. Each member can be changed individually afterwards. Omitted in `concise`."},"default_signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"description":"Default signal bucket of the list, overridable per member. Recorded and returned only — it changes no behaviour today. Omitted in `concise`."},"archived_at":{"type":"string","format":"date-time","nullable":true,"description":"When the list was archived, or null while it is in use. An archived list keeps every member, but drops out of `GET /v2/lists` unless you ask for it. Omitted in `concise`."},"persona_ids":{"type":"array","items":{"type":"integer"},"description":"The personas this list belongs to. An empty array means the list applies to every persona. Omitted in `concise`."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `list_id`."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/lists/{kind}/{list_id}/members":{"get":{"tags":["V2 Lists"],"summary":"List members","description":"Returns a paginated list of the list's members, each with its own tracking status and signal bucket (null when it follows the list default).","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number (starts at 1). Defaults to 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":25},"description":"Items per page. Defaults to 25, max 100."},{"name":"response_format","in":"query","required":false,"schema":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized"},"description":"Verbosity: `concise` (id/kind/type/name only), `normalized` (default, adds description, counts and the list defaults), `detailed` (identical to normalized; lists carry no heavy payload). A `concise` list is exactly `{ id, kind, type, name }` — every other field documented below is absent from it, not null."},{"name":"q","in":"query","required":false,"schema":{"type":"string","minLength":1,"maxLength":255},"description":"Search members by name, LinkedIn handle, or (for people) current company name. Case-insensitive, matches anywhere in the text."}],"responses":{"200":{"description":"Paginated members.","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id"],"description":"A member, a company (with `name`) or a person (with `first_name`/`last_name`).","properties":{"id":{"type":"integer","description":"Numeric id of the canonical company or profile."},"name":{"type":"string","nullable":true,"description":"Company members only."},"first_name":{"type":"string","nullable":true,"description":"Profile members only."},"last_name":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_handle":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true,"description":"Company members only. URL of the company's logo image, when available."},"avatar_url":{"type":"string","nullable":true,"description":"Profile members only."},"position":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_headline":{"type":"string","nullable":true,"description":"Profile members only."},"enrichment_status":{"type":"string","nullable":true,"description":"Profile members only."},"current_company":{"type":"object","nullable":true,"description":"Profile members only. The profile's current company, if known.","properties":{"name":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true}}},"tracking_status":{"type":"string","enum":["followed","unfollowed"],"nullable":true,"description":"This member's tracking status. Set to the list's `default_tracking_status` when the member joins, and changed per member from there."},"signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"nullable":true,"description":"This member's own signal bucket. Null means it follows the list's `default_signal_bucket`."}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer"},"page_size":{"type":"integer"},"page_count":{"type":"integer"},"total":{"type":"integer"}}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `list_id` or query parameters."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"post":{"tags":["V2 Lists"],"summary":"Add members","description":"Adds companies or people to a list. Identify each member by LinkedIn URL or handle (preferred). For company lists only, a `domain` is accepted as a fallback when no LinkedIn identifier is available.\n\nA member that cannot be added (a `domain` on a list of people, a LinkedIn URL of the other kind, or a value that is not a usable identifier) is reported in `errors` and never blocks the other members.\n\nOn champion lists, each member can also carry `company` — the company where you know this contact — so we can detect if they change jobs. Providing `company` on any other list returns a hard **422**.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["members"],"properties":{"members":{"type":"array","minItems":1,"maxItems":100,"items":{"type":"object","description":"Identify the entity by linkedin_url or linkedin_handle (preferred). For company watchlists only, domain is accepted as a fallback when no LinkedIn identifier is available.","properties":{"linkedin_url":{"type":"string","description":"LinkedIn URL of the company or person. The `https://` is optional (\"linkedin.com/company/stripe\" works)."},"linkedin_handle":{"type":"string"},"domain":{"type":"string","description":"Company domain (e.g. \"stripe.com\"). Accepted as a fallback for company watchlists only when no LinkedIn URL or handle is available. Providing a domain on a profile watchlist, or a value without an extension such as \".com\", is reported in `errors` and does not block the other members."},"company":{"type":"object","description":"The company where you know this contact — used to detect when they change jobs. Only supported on champion watchlists; providing it on any other watchlist returns 422. Provide at least one of name or domain.","properties":{"name":{"type":"string"},"domain":{"type":"string"}}}},"anyOf":[{"required":["linkedin_url"]},{"required":["linkedin_handle"]},{"required":["domain"]}]}}}}}}},"responses":{"200":{"description":"Members added. Per-member failures are reported in `errors`; re-adding a member that is already on the list is a success and returns it in neither array.","content":{"application/json":{"schema":{"type":"object","required":["data","errors"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id"],"description":"A member, a company (with `name`) or a person (with `first_name`/`last_name`).","properties":{"id":{"type":"integer","description":"Numeric id of the canonical company or profile."},"name":{"type":"string","nullable":true,"description":"Company members only."},"first_name":{"type":"string","nullable":true,"description":"Profile members only."},"last_name":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_handle":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true,"description":"Company members only. URL of the company's logo image, when available."},"avatar_url":{"type":"string","nullable":true,"description":"Profile members only."},"position":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_headline":{"type":"string","nullable":true,"description":"Profile members only."},"enrichment_status":{"type":"string","nullable":true,"description":"Profile members only."},"current_company":{"type":"object","nullable":true,"description":"Profile members only. The profile's current company, if known.","properties":{"name":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true}}},"tracking_status":{"type":"string","enum":["followed","unfollowed"],"nullable":true,"description":"This member's tracking status. Set to the list's `default_tracking_status` when the member joins, and changed per member from there."},"signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"nullable":true,"description":"This member's own signal bucket. Null means it follows the list's `default_signal_bucket`."}}}},"errors":{"type":"array","items":{"type":"object","required":["input","code","message"],"properties":{"input":{"type":"object","description":"The entity input that failed.","properties":{"linkedin_url":{"type":"string"},"linkedin_handle":{"type":"string"},"domain":{"type":"string"}}},"code":{"type":"string","enum":["multiple_domain_matches","apollo_failed","resolution_failed","wrong_entity_type","invalid_identifier"],"description":"`multiple_domain_matches`, the domain matched more than one company; `apollo_failed`, the company could not be resolved from its domain; `resolution_failed`, an unexpected error occurred during resolution; `wrong_entity_type`, the member is a company on a list of people or a person on a list of companies; `invalid_identifier`, the value is not a usable LinkedIn URL, handle or domain (for example a domain with no extension such as \".com\")."},"message":{"type":"string","description":"Human-readable failure detail."}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"This list's membership is managed automatically and cannot be changed by hand."},"422":{"description":"No member could be added because every one failed (see `errors`), or the request body is invalid. Re-adding already-present members returns 200, not 422.","content":{"application/json":{"schema":{"type":"object","required":["data","errors"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id"],"description":"A member, a company (with `name`) or a person (with `first_name`/`last_name`).","properties":{"id":{"type":"integer","description":"Numeric id of the canonical company or profile."},"name":{"type":"string","nullable":true,"description":"Company members only."},"first_name":{"type":"string","nullable":true,"description":"Profile members only."},"last_name":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_handle":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true,"description":"Company members only. URL of the company's logo image, when available."},"avatar_url":{"type":"string","nullable":true,"description":"Profile members only."},"position":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_headline":{"type":"string","nullable":true,"description":"Profile members only."},"enrichment_status":{"type":"string","nullable":true,"description":"Profile members only."},"current_company":{"type":"object","nullable":true,"description":"Profile members only. The profile's current company, if known.","properties":{"name":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true}}},"tracking_status":{"type":"string","enum":["followed","unfollowed"],"nullable":true,"description":"This member's tracking status. Set to the list's `default_tracking_status` when the member joins, and changed per member from there."},"signal_bucket":{"type":"string","enum":["bucket_1","bucket_2","bucket_3"],"nullable":true,"description":"This member's own signal bucket. Null means it follows the list's `default_signal_bucket`."}}},"maxItems":0},"errors":{"type":"array","items":{"type":"object","required":["input","code","message"],"properties":{"input":{"type":"object","description":"The entity input that failed.","properties":{"linkedin_url":{"type":"string"},"linkedin_handle":{"type":"string"},"domain":{"type":"string"}}},"code":{"type":"string","enum":["multiple_domain_matches","apollo_failed","resolution_failed","wrong_entity_type","invalid_identifier"],"description":"`multiple_domain_matches`, the domain matched more than one company; `apollo_failed`, the company could not be resolved from its domain; `resolution_failed`, an unexpected error occurred during resolution; `wrong_entity_type`, the member is a company on a list of people or a person on a list of companies; `invalid_identifier`, the value is not a usable LinkedIn URL, handle or domain (for example a domain with no extension such as \".com\")."},"message":{"type":"string","description":"Human-readable failure detail."}}}}}}}}},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/lists/{kind}/{list_id}/members/{member_id}":{"delete":{"tags":["V2 Lists"],"summary":"Remove member","description":"Removes one member from a list by its member id.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."},{"name":"member_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Numeric id of the member (the `id` returned by the members endpoint)."}],"responses":{"200":{"description":"The removed member id.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","deleted"],"properties":{"id":{"type":"integer"},"deleted":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"This list's membership is managed automatically and cannot be changed by hand."},"422":{"description":"Invalid `list_id` or `member_id`."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/lists/{kind}/{list_id}/members/{member_id}/tracking-status":{"patch":{"tags":["V2 Lists"],"summary":"Set a member's tracking status","description":"Overrides one member's tracking status, independent of the list's own default — for example, keeping a single account followed inside an otherwise unfollowed tier, or the reverse. An unfollowed account is not scraped for new signals and does not consume credits. Pass `tracking_status: null` to clear the override and go back to following the list default. Only real changes are recorded in the list's membership log; setting a value the member already has writes nothing.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."},{"name":"member_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Numeric id of the member (the `id` returned by the members endpoint)."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["tracking_status"],"properties":{"tracking_status":{"type":"string","enum":["followed","unfollowed"],"nullable":true,"description":"The override to set, or null to clear it and follow the list default again."}}}}}},"responses":{"200":{"description":"The member and its tracking status after the change.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","tracking_status"],"properties":{"id":{"type":"integer"},"tracking_status":{"type":"string","enum":["followed","unfollowed"],"nullable":true,"description":"The member's own override, not the effective status — null means it now follows the list default."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid parameters or request body."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/lists/{kind}/{list_id}/membership-logs":{"get":{"tags":["V2 Lists"],"summary":"List membership history","description":"Returns the list's membership history — every time an account or person entered or left, and every tracking-status change, newest first. Only real changes are recorded; a sync that re-confirms an existing member writes nothing.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"Whether the list holds companies or people, matching its `type`. Part of the path so the two id spaces never collide."},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the list."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number (starts at 1). Defaults to 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":25},"description":"Items per page. Defaults to 25, max 100."}],"responses":{"200":{"description":"Paginated membership history, newest first.","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id","transition","reason","created_at"],"properties":{"id":{"type":"integer","description":"Numeric id of the log entry."},"transition":{"type":"string","enum":["entered","left","owner_changed","tracking_status_changed","bucket_changed"],"description":"What kind of change this entry records."},"reason":{"type":"string","enum":["manual","csv_import","api","rule_match","rule_unmatch","mode_switch"],"description":"Why the transition happened."},"reason_detail":{"type":"object","nullable":true,"additionalProperties":true,"description":"Narrow, non-free-text context: `{ \"userEmail\": \"...\" }` for a person-driven change, `{ \"ruleGroupId\": \"...\" }` for a rule-driven one. Null when the transition carries no further context."},"previous_value":{"type":"string","nullable":true,"description":"Prior value, for a `tracking_status_changed` entry."},"new_value":{"type":"string","nullable":true,"description":"New value, for a `tracking_status_changed` entry."},"created_at":{"type":"string","format":"date-time"},"membership_id":{"type":"integer","nullable":true,"description":"The membership this entry is about. Null once that membership no longer exists (a `left` entry outlives it by design)."},"entity_id":{"type":"integer","nullable":true,"description":"The workspace-scoped company or person this entry is about."},"actor_user_id":{"type":"integer","nullable":true,"description":"The workspace user who acted, when the transition was person-driven."}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer"},"page_size":{"type":"integer"},"page_count":{"type":"integer"},"total":{"type":"integer"}}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `list_id` or query parameters."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/watchlists":{"post":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"Create watchlist","description":"Creates a reusable, workspace-scoped watchlist. `kind` is derived from the immutable `type`.","security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["type","title"],"properties":{"type":{"type":"string","enum":["competitor","partner","customer","influencer","champion"],"description":"Immutable; determines the list kind."},"title":{"type":"string","minLength":1},"description":{"type":"string"}}}}}},"responses":{"201":{"description":"The created watchlist.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","kind","type","title"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the watchlist."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","influencer","champion"],"description":"Immutable list type. competitor/partner/customer → a company list; influencer/champion → a profile list."},"title":{"type":"string"},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"entity_count":{"type":"integer","description":"Member count. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents bound to this list. Omitted in `concise`."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Invalid request body."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"get":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"List watchlists","description":"Returns a paginated list of the workspace's watchlists. The total is in `meta.pagination`.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number (starts at 1). Defaults to 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":25},"description":"Items per page. Defaults to 25, max 100."},{"name":"type","in":"query","required":false,"schema":{"type":"string","enum":["competitor","partner","customer","influencer","champion"]},"description":"Optional filter by list type."},{"name":"response_format","in":"query","required":false,"schema":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized"},"description":"Verbosity: `concise` (id/kind/type/title only), `normalized` (default, adds description + counts), `detailed` (identical to normalized; watchlists carry no heavy payload)."}],"responses":{"200":{"description":"Paginated watchlists.","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id","kind","type","title"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the watchlist."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","influencer","champion"],"description":"Immutable list type. competitor/partner/customer → a company list; influencer/champion → a profile list."},"title":{"type":"string"},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"entity_count":{"type":"integer","description":"Member count. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents bound to this list. Omitted in `concise`."}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer"},"page_size":{"type":"integer"},"page_count":{"type":"integer"},"total":{"type":"integer"}}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"422":{"description":"Invalid query parameters."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/watchlists/{kind}/{watchlist_id}":{"get":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"Get watchlist","description":"Fetches one watchlist by its numeric id.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."},{"name":"response_format","in":"query","required":false,"schema":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized"},"description":"Verbosity: `concise` (id/kind/type/title only), `normalized` (default, adds description + counts), `detailed` (identical to normalized; watchlists carry no heavy payload)."}],"responses":{"200":{"description":"The watchlist.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","kind","type","title"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the watchlist."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","influencer","champion"],"description":"Immutable list type. competitor/partner/customer → a company list; influencer/champion → a profile list."},"title":{"type":"string"},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"entity_count":{"type":"integer","description":"Member count. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents bound to this list. Omitted in `concise`."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `watchlist_id`."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"put":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"Update watchlist","description":"Updates the title and/or description. The list `type` is immutable.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","description":"`type` is immutable and is ignored if provided.","properties":{"title":{"type":"string","minLength":1},"description":{"type":"string","nullable":true,"description":"Pass null to clear."}}}}}},"responses":{"200":{"description":"The updated watchlist.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","kind","type","title"],"properties":{"id":{"type":"integer","description":"Numeric identifier of the watchlist."},"kind":{"type":"string","enum":["company","profile"],"description":"Derived from `type` (read-only)."},"type":{"type":"string","enum":["competitor","partner","customer","influencer","champion"],"description":"Immutable list type. competitor/partner/customer → a company list; influencer/champion → a profile list."},"title":{"type":"string"},"description":{"type":"string","nullable":true,"description":"Omitted in the `concise` response format."},"entity_count":{"type":"integer","description":"Member count. Omitted in `concise`."},"bound_agent_count":{"type":"integer","description":"Number of agents bound to this list. Omitted in `concise`."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `watchlist_id` or request body."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"delete":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"Delete watchlist","description":"Deletes a watchlist. Fails with 409 if one or more agents are still bound to it.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."}],"responses":{"200":{"description":"The deleted watchlist id.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id"],"properties":{"id":{"type":"integer"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"The watchlist is bound to one or more agents; unbind first."},"422":{"description":"Invalid `watchlist_id`."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/watchlists/{kind}/{watchlist_id}/entities":{"get":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"List watchlist entities","description":"Returns a paginated list of the watchlist's members.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number (starts at 1). Defaults to 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":25},"description":"Items per page. Defaults to 25, max 100."},{"name":"response_format","in":"query","required":false,"schema":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized"},"description":"Verbosity: `concise` (id/kind/type/title only), `normalized` (default, adds description + counts), `detailed` (identical to normalized; watchlists carry no heavy payload)."},{"name":"q","in":"query","required":false,"schema":{"type":"string","minLength":1,"maxLength":255},"description":"Search members by name, LinkedIn handle, or (for people) current company name. Case-insensitive, matches anywhere in the text."}],"responses":{"200":{"description":"Paginated members.","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id"],"description":"A member, a company (with `name`) or a person (with `first_name`/`last_name`).","properties":{"id":{"type":"integer","description":"Numeric id of the canonical company or profile."},"name":{"type":"string","nullable":true,"description":"Company members only."},"first_name":{"type":"string","nullable":true,"description":"Profile members only."},"last_name":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_handle":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true,"description":"Company members only. URL of the company's logo image, when available."},"avatar_url":{"type":"string","nullable":true,"description":"Profile members only."},"position":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_headline":{"type":"string","nullable":true,"description":"Profile members only."},"enrichment_status":{"type":"string","nullable":true,"description":"Profile members only."},"current_company":{"type":"object","nullable":true,"description":"Profile members only. The profile's current company, if known.","properties":{"name":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true}}}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer"},"page_size":{"type":"integer"},"page_count":{"type":"integer"},"total":{"type":"integer"}}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `watchlist_id` or query parameters."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}},"post":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"Add watchlist entities","description":"Adds members to a watchlist. Identify each entity by LinkedIn URL or handle (preferred). For company watchlists only, a `domain` is accepted as a fallback when no LinkedIn identifier is available.\n\nThe call is **partial-success**: members that were successfully added appear in `data`; per-entity failures appear in `errors`. A **200** response means the request was accepted, inspect `errors` to check for any per-entity failures. Re-adding members that are already present is safe and returns **200** with an empty `data` array. If **no** entities could be added because every one failed, the response is **422** with `data: []` and `errors` populated.\n\nA member that cannot be added (a `domain` on a profile watchlist, a LinkedIn URL of the other kind, or a value that is not a usable identifier) is reported in `errors` and never blocks the other members.\n\nOn champion watchlists, each entity can also carry `company` — the company where you know this contact — so we can detect if they change jobs. Providing `company` on any other watchlist returns a hard **422**.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["entities"],"properties":{"entities":{"type":"array","minItems":1,"maxItems":100,"items":{"type":"object","description":"Identify the entity by linkedin_url or linkedin_handle (preferred). For company watchlists only, domain is accepted as a fallback when no LinkedIn identifier is available.","properties":{"linkedin_url":{"type":"string","description":"LinkedIn URL of the company or person. The `https://` is optional (\"linkedin.com/company/stripe\" works)."},"linkedin_handle":{"type":"string"},"domain":{"type":"string","description":"Company domain (e.g. \"stripe.com\"). Accepted as a fallback for company watchlists only when no LinkedIn URL or handle is available. Providing a domain on a profile watchlist, or a value without an extension such as \".com\", is reported in `errors` and does not block the other members."},"company":{"type":"object","description":"The company where you know this contact — used to detect when they change jobs. Only supported on champion watchlists; providing it on any other watchlist returns 422. Provide at least one of name or domain.","properties":{"name":{"type":"string"},"domain":{"type":"string"}}}},"anyOf":[{"required":["linkedin_url"]},{"required":["linkedin_handle"]},{"required":["domain"]}]}}}}}}},"responses":{"200":{"description":"Request accepted. `data` contains any newly-added members (empty if all were already present); `errors` lists any per-entity failures.","content":{"application/json":{"schema":{"type":"object","required":["data","errors"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id"],"description":"A member, a company (with `name`) or a person (with `first_name`/`last_name`).","properties":{"id":{"type":"integer","description":"Numeric id of the canonical company or profile."},"name":{"type":"string","nullable":true,"description":"Company members only."},"first_name":{"type":"string","nullable":true,"description":"Profile members only."},"last_name":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_handle":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true,"description":"Company members only. URL of the company's logo image, when available."},"avatar_url":{"type":"string","nullable":true,"description":"Profile members only."},"position":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_headline":{"type":"string","nullable":true,"description":"Profile members only."},"enrichment_status":{"type":"string","nullable":true,"description":"Profile members only."},"current_company":{"type":"object","nullable":true,"description":"Profile members only. The profile's current company, if known.","properties":{"name":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true}}}}}},"errors":{"type":"array","items":{"type":"object","required":["input","code","message"],"properties":{"input":{"type":"object","description":"The entity input that failed.","properties":{"linkedin_url":{"type":"string"},"linkedin_handle":{"type":"string"},"domain":{"type":"string"}}},"code":{"type":"string","enum":["multiple_domain_matches","apollo_failed","resolution_failed","wrong_entity_type","invalid_identifier"],"description":"`multiple_domain_matches`, the domain matched more than one company; `apollo_failed`, the company could not be resolved from its domain; `resolution_failed`, an unexpected error occurred during resolution; `wrong_entity_type`, the member is a company on a list of people or a person on a list of companies; `invalid_identifier`, the value is not a usable LinkedIn URL, handle or domain (for example a domain with no extension such as \".com\")."},"message":{"type":"string","description":"Human-readable failure detail."}}},"description":"Per-entity failures. Empty when all entities were added successfully."}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"This watchlist's membership is managed automatically and cannot be changed by hand."},"422":{"description":"No entities could be added because every one failed (see `errors` for details), or the request body is invalid. Re-adding already-present members returns 200, not 422.","content":{"application/json":{"schema":{"type":"object","required":["data","errors"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id"],"description":"A member, a company (with `name`) or a person (with `first_name`/`last_name`).","properties":{"id":{"type":"integer","description":"Numeric id of the canonical company or profile."},"name":{"type":"string","nullable":true,"description":"Company members only."},"first_name":{"type":"string","nullable":true,"description":"Profile members only."},"last_name":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_handle":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true,"description":"Company members only. URL of the company's logo image, when available."},"avatar_url":{"type":"string","nullable":true,"description":"Profile members only."},"position":{"type":"string","nullable":true,"description":"Profile members only."},"linkedin_headline":{"type":"string","nullable":true,"description":"Profile members only."},"enrichment_status":{"type":"string","nullable":true,"description":"Profile members only."},"current_company":{"type":"object","nullable":true,"description":"Profile members only. The profile's current company, if known.","properties":{"name":{"type":"string","nullable":true},"logo_url":{"type":"string","nullable":true}}}}},"maxItems":0},"errors":{"type":"array","items":{"type":"object","required":["input","code","message"],"properties":{"input":{"type":"object","description":"The entity input that failed.","properties":{"linkedin_url":{"type":"string"},"linkedin_handle":{"type":"string"},"domain":{"type":"string"}}},"code":{"type":"string","enum":["multiple_domain_matches","apollo_failed","resolution_failed","wrong_entity_type","invalid_identifier"],"description":"`multiple_domain_matches`, the domain matched more than one company; `apollo_failed`, the company could not be resolved from its domain; `resolution_failed`, an unexpected error occurred during resolution; `wrong_entity_type`, the member is a company on a list of people or a person on a list of companies; `invalid_identifier`, the value is not a usable LinkedIn URL, handle or domain (for example a domain with no extension such as \".com\")."},"message":{"type":"string","description":"Human-readable failure detail."}}}}}}}}},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/watchlists/{kind}/{watchlist_id}/entities/{entity_id}":{"delete":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"Remove watchlist entity","description":"Removes one member from a watchlist by its entity id.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."},{"name":"entity_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Numeric id of the member (the `id` returned by the list-entities endpoint)."}],"responses":{"200":{"description":"Removal result.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","deleted"],"properties":{"id":{"type":"integer"},"deleted":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"409":{"description":"This watchlist's membership is managed automatically and cannot be changed by hand."},"422":{"description":"Invalid path parameters."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/watchlists/{kind}/{watchlist_id}/entities/{entity_id}/tracking-status":{"patch":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"Set entity tracking status","description":"Overrides one member's tracking status, independent of the watchlist's own default — for example, keeping a single account followed inside an otherwise unfollowed tier, or the reverse. An unfollowed account is not scraped for new signals and does not consume credits. Pass `tracking_status: null` to clear the override and go back to following the watchlist's default. Only real changes are recorded in the watchlist's membership log; setting a value the member already has writes nothing.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."},{"name":"entity_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Numeric id of the member (the `id` returned by the list-entities endpoint)."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["tracking_status"],"properties":{"tracking_status":{"type":"string","enum":["followed","unfollowed"],"nullable":true,"description":"The override to set, or null to clear it and inherit the watchlist default again."}}}}}},"responses":{"200":{"description":"The member's tracking-status override after the write.","content":{"application/json":{"schema":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id","tracking_status"],"properties":{"id":{"type":"integer"},"tracking_status":{"type":"string","enum":["followed","unfollowed"],"nullable":true,"description":"The member's own override, not the effective (COALESCE'd) status — null means it now inherits the watchlist default."}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid path parameters or request body."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}},"/v2/watchlists/{kind}/{watchlist_id}/membership-logs":{"get":{"tags":["V2 Watchlists"],"deprecated":true,"summary":"List watchlist membership log","description":"Returns the watchlist's membership history — every time an account or person entered or left, newest first. Only real changes are recorded; a sync that re-confirms an existing member writes nothing.","security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"kind","in":"path","required":true,"schema":{"type":"string","enum":["company","profile"]},"description":"The watchlist kind (company or profile), matching the list `type`. Part of the path so the company and profile id spaces never collide."},{"name":"watchlist_id","in":"path","required":true,"schema":{"type":"integer"},"description":"Identifier of the watchlist."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1},"description":"Page number (starts at 1). Defaults to 1."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":25},"description":"Items per page. Defaults to 25, max 100."}],"responses":{"200":{"description":"Paginated membership log entries.","content":{"application/json":{"schema":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id","transition","reason","created_at"],"properties":{"id":{"type":"integer","description":"Numeric id of the log entry."},"transition":{"type":"string","enum":["entered","left","owner_changed","tracking_status_changed","bucket_changed"],"description":"What kind of change this entry records."},"reason":{"type":"string","enum":["manual","csv_import","api","rule_match","rule_unmatch","mode_switch"],"description":"Why the transition happened."},"reason_detail":{"type":"object","nullable":true,"additionalProperties":true,"description":"Narrow, non-free-text context: `{ \"userEmail\": \"...\" }` for a person-driven change, `{ \"ruleGroupId\": \"...\" }` for a rule-driven one. Null when the transition carries no further context."},"previous_value":{"type":"string","nullable":true,"description":"Prior value, for a `tracking_status_changed` entry."},"new_value":{"type":"string","nullable":true,"description":"New value, for a `tracking_status_changed` entry."},"created_at":{"type":"string","format":"date-time"},"membership_id":{"type":"integer","nullable":true,"description":"The membership this entry is about. Null once that membership no longer exists (a `left` entry outlives it by design)."},"entity_id":{"type":"integer","nullable":true,"description":"The workspace-scoped company or person this entry is about."},"actor_user_id":{"type":"integer","nullable":true,"description":"The workspace user who acted, when the transition was person-driven."}}}},"meta":{"type":"object","required":["pagination"],"properties":{"pagination":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer"},"page_size":{"type":"integer"},"page_count":{"type":"integer"},"total":{"type":"integer"}}}}}}}}}},"401":{"$ref":"#/components/responses/V2Unauthorized"},"404":{"$ref":"#/components/responses/V2NotFound"},"422":{"description":"Invalid `watchlist_id` or query parameters."},"429":{"$ref":"#/components/responses/V2TooManyRequests"},"500":{"$ref":"#/components/responses/V2InternalServerError"}}}}},"components":{"securitySchemes":{"ApiKeyAuth":{"type":"http","scheme":"bearer","bearerFormat":"API Key","description":"API key authentication. Use your API key as the bearer token.\n\nFormat: `sk_live_...`\n\nExample: `Authorization: Bearer sk_live_abc123...`"},"PartnerMasterKeyAuth":{"type":"http","scheme":"bearer","bearerFormat":"Master Key","description":"Partner master key authentication, for partner-level (not workspace-level) routes.\n\nFormat: `mk_live_...`\n\nExample: `Authorization: Bearer mk_live_abc123...`"}},"responses":{"V2BadRequest":{"description":"Bad request, invalid query parameters or path params","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2Unauthorized":{"description":"Unauthorized, invalid or missing API key","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2Forbidden":{"description":"Forbidden, feature not enabled for this workspace","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2QuotaExceeded":{"description":"Forbidden, the limited_trial cumulative top-account quota would be exceeded by this request. No accounts from the request are ingested (hard reject, no partial ingestion). `type` is `https://docs.getsillage.com/errors/top-account-quota-exceeded`, distinct from the generic forbidden `type`.","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"},"example":{"type":"https://docs.getsillage.com/errors/top-account-quota-exceeded","title":"Top account quota exceeded","status":403,"detail":"Adding 10 account(s) would exceed the top-account quota (15/20 used)."}}}},"V2NotFound":{"description":"Not found","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2InternalServerError":{"description":"Internal server error","headers":{"X-Request-Id":{"description":"Unique identifier for this request, include this when reporting errors","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2UnprocessableEntity":{"description":"Unprocessable entity, invalid route parameters or request body","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2Conflict":{"description":"Conflict, resource state prevents this operation","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2PaymentRequired":{"description":"Payment required, insufficient credits","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}},"V2TooManyRequests":{"description":"Too many requests, rate limit exceeded","headers":{"X-Request-Id":{"description":"Unique identifier for this request","schema":{"type":"string","format":"uuid"}},"X-RateLimit-Limit":{"description":"Maximum number of requests allowed in the window","schema":{"type":"integer"}},"X-RateLimit-Remaining":{"description":"Number of requests remaining in the current window","schema":{"type":"integer"}},"Retry-After":{"description":"Number of seconds to wait before retrying","schema":{"type":"integer"}}},"content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/ProblemDetails"}}}}},"schemas":{"ProblemDetails":{"type":"object","description":"RFC 9457 error body. Returned with Content-Type: application/problem+json on every v2 error response.","required":["type","title","status"],"properties":{"type":{"type":"string","format":"uri","description":"A URI that identifies the problem type. `about:blank` when the type is unspecified (e.g. 500).","example":"https://docs.getsillage.com/errors/invalid-query"},"title":{"type":"string","description":"A short, human-readable summary of the problem type. Stable across occurrences.","example":"Invalid query parameters"},"status":{"type":"integer","description":"The HTTP status code.","example":400},"detail":{"type":"string","description":"A human-readable explanation specific to this occurrence.","example":"page_size must be a positive integer"},"instance":{"type":"string","description":"The request path that produced this error.","example":"/api/v2/contents"},"errors":{"type":"object","description":"Field-level validation errors. Present only on 400/422 validation failures.","additionalProperties":{"type":"array","items":{"type":"string"}},"example":{"page_size":["must be a positive integer"]}}}},"PersonaLaunch":{"type":"object","description":"One persona this call considered.","required":["persona_id","request_id","status","credits"],"properties":{"persona_id":{"type":"integer","description":"Numeric id of the persona."},"request_id":{"type":"integer","nullable":true,"description":"Numeric id of this persona's own enrichment content request. Null when the persona was skipped, since no request was created for it."},"status":{"type":"string","enum":["launched","already_requested","skipped_no_location","skipped_no_job_titles"],"description":"`launched` — a new request was created and charged. `already_requested` — already enriched today for this company, at no extra cost. `skipped_no_location` / `skipped_no_job_titles` — this persona has no location or no job titles set, so it was not enriched."},"credits":{"type":"integer","description":"Credits charged for this persona by this call — 1 when `launched`, 0 otherwise."}}},"PersonaLaunchProblemDetails":{"description":"The enrich-company-mapping endpoint's 422 error body: the standard problem details, plus a per-persona breakdown.","allOf":[{"$ref":"#/components/schemas/ProblemDetails"},{"type":"object","required":["launches"],"properties":{"launches":{"type":"array","description":"One entry per persona this call considered.","items":{"$ref":"#/components/schemas/PersonaLaunch"}}}}]},"EnrichPersonaIds":{"type":"array","nullable":true,"minItems":1,"items":{"type":"integer"},"description":"Specific personas to enrich. Omit to enrich the personas linked to the lists this company belongs to (every active persona when none of those lists names one, or when the company is on no list). An id that is not one of your active personas returns a 422.","example":[501,502]},"CompetitorActivityData":{"type":"object","required":["interaction","post"],"description":"Interaction data for competitor activity signals","properties":{"interaction":{"type":"object","properties":{"type":{"type":"string","enum":["comment","reaction"]},"url":{"type":"string","nullable":true},"author":{"type":"object","properties":{"full_name":{"type":"string","nullable":true},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"role":{"type":"string","nullable":true},"comment_text":{"type":"string","nullable":true}}},"content_id":{"type":"integer","nullable":true,"description":"ID of the content behind this interaction. Fetch the full post via the Contents endpoints. Null when no matching content exists in your workspace."}}},"post":{"type":"object","properties":{"url":{"type":"string","nullable":true},"extract":{"type":"string","nullable":true},"author":{"type":"object","properties":{"full_name":{"type":"string","nullable":true},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"role":{"type":"string","nullable":true}}}}}}},"KeywordDetectionData":{"type":"object","required":["post","keywords_found"],"properties":{"post":{"type":"object","properties":{"url":{"type":"string","nullable":true},"extract":{"type":"string","nullable":true},"author":{"type":"object","properties":{"full_name":{"type":"string","nullable":true},"headline":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true}}}}},"keywords_found":{"type":"array","items":{"type":"string"}}}},"JobUpdateData":{"type":"object","required":["previous_position","new_position"],"properties":{"previous_position":{"type":"object","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true}}},"new_position":{"type":"object","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"start_date":{"type":"string","format":"date","description":"Start date of the new position in YYYY-MM-DD format (day may default to 01 when only month is available)","nullable":true}}}}},"ContentEngagementData":{"type":"object","required":["interaction","post"],"description":"Interaction data for content engagement signals","properties":{"interaction":{"type":"object","properties":{"type":{"type":"string","enum":["comment","reaction"]},"url":{"type":"string","nullable":true},"author":{"type":"object","properties":{"full_name":{"type":"string","nullable":true},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"role":{"type":"string","nullable":true},"comment_text":{"type":"string","nullable":true}}}}},"post":{"type":"object","properties":{"url":{"type":"string","nullable":true},"extract":{"type":"string","nullable":true},"author":{"type":"object","properties":{"full_name":{"type":"string","nullable":true},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"role":{"type":"string","nullable":true}}}}}}},"InfluencerEngagementData":{"type":"object","required":["interaction","post"],"description":"Interaction data for influencer engagement signals","properties":{"interaction":{"type":"object","properties":{"type":{"type":"string","enum":["comment","reaction"]},"url":{"type":"string","nullable":true},"author":{"type":"object","properties":{"full_name":{"type":"string","nullable":true},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"role":{"type":"string","nullable":true},"comment_text":{"type":"string","nullable":true}}}}},"post":{"type":"object","properties":{"url":{"type":"string","nullable":true},"extract":{"type":"string","nullable":true},"author":{"type":"object","properties":{"full_name":{"type":"string","nullable":true},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"role":{"type":"string","nullable":true}}}}}}},"DeepSearchData":{"type":"object","description":"Deep search signal data (AI-generated company intelligence)","properties":{"title":{"type":"string","nullable":true,"description":"Signal title"},"tag":{"type":"string","nullable":true,"description":"Deep search signal subtype (e.g. funding, hiring, expansion)"},"date":{"type":"string","nullable":true,"description":"Date of the event (YYYY-MM-DD)"},"sources":{"type":"array","nullable":true,"items":{"type":"object","properties":{"url":{"type":"string","nullable":true},"excerpts":{"type":"array","nullable":true,"items":{"type":"string"}}}}}}},"JobPostingData":{"type":"object","description":"Job posting signal data","properties":{"posting":{"type":"object","nullable":true,"properties":{"title":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"job_url":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"description":{"type":"string","nullable":true},"published_at":{"type":"string","nullable":true}}},"job_title":{"type":"string","nullable":true,"description":"Searched job title that matched this posting"},"insight":{"type":"object","nullable":true,"description":"AI insight analysis result (only for job_posting_insight signals)","properties":{"is_match":{"type":"boolean","description":"Whether the posting matches the search criteria"},"tag":{"type":"string","nullable":true},"reasoning":{"type":"string","nullable":true}}}}},"JobPostingKeywordDetectionData":{"type":"object","description":"Job posting keyword detection signal data","properties":{"keywords_found":{"type":"array","items":{"type":"string"},"description":"The tracked keywords found in the job posting"},"posting":{"type":"object","properties":{"title":{"type":"string","nullable":true,"description":"Title of the job posting"},"job_url":{"type":"string","nullable":true,"description":"Link to the job posting"}}}}},"ChampionTrackingData":{"type":"object","required":["change_type","previous_position","new_position"],"properties":{"change_type":{"type":"string","nullable":true},"previous_position":{"type":"object","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true}}},"new_position":{"type":"object","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"start_date":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true}}}}},"V2PaginationMeta":{"type":"object","required":["page","page_size","page_count","total"],"properties":{"page":{"type":"integer","description":"Current page number"},"page_size":{"type":"integer","description":"Number of items per page"},"page_count":{"type":"integer","description":"Total number of pages"},"total":{"type":"integer","description":"Total number of matching items"}}},"V2Persona":{"type":"object","required":["id"],"properties":{"id":{"type":"integer","description":"ID of the persona, as returned by `GET /v2/personas`. This ID is specific to your environment.","example":1234},"job_title":{"type":"array","items":{"type":"string"},"nullable":true},"exclude_job_title":{"type":"array","items":{"type":"string"},"nullable":true},"location":{"type":"array","items":{"type":"string"},"nullable":true},"headcount":{"type":"array","items":{"type":"string"},"nullable":true},"industry":{"type":"array","items":{"type":"string"},"nullable":true},"seniority":{"type":"array","items":{"type":"string"},"nullable":true},"additional_info":{"type":"string","nullable":true},"tag":{"type":"string","nullable":true,"description":"Short free-form label you can set to recognise this persona in your own systems. Never used for targeting, and unique across the personas of a workspace."}}},"V2PersonaBody":{"type":"object","required":["job_title","location"],"properties":{"job_title":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Required. Target job titles — at least one value."},"exclude_job_title":{"type":"array","items":{"type":"string"},"description":"Job titles to exclude."},"location":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Required. Target locations — at least one value. Use country or region names (e.g. \"EMEA\"); a city-only list saves but will not match any country, so account mapping will not run for it."},"headcount":{"type":"array","items":{"type":"string"},"description":"Target headcount ranges (enum values)."},"industry":{"type":"array","items":{"type":"string"},"description":"Target industries."},"seniority":{"type":"array","items":{"type":"string"},"description":"Target seniority levels (enum values)."},"additional_info":{"type":"string","description":"Additional free-text persona context."},"tag":{"type":"string","maxLength":255,"description":"Short free-form label you can set to recognise this persona in your own systems. Never used for targeting. Two personas of the same workspace cannot share a tag — reusing one returns 409. Omit it to leave the persona untagged."}}},"V2PersonaPatchBody":{"type":"object","description":"Every field is optional, but at least one must be provided.","properties":{"job_title":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Target job titles — at least one value, if sent."},"exclude_job_title":{"type":"array","items":{"type":"string"},"description":"Job titles to exclude."},"location":{"type":"array","items":{"type":"string"},"minItems":1,"description":"Target locations — at least one value, if sent. Use country or region names (e.g. \"EMEA\"); a city-only list saves but will not match any country, so account mapping will not run for it."},"headcount":{"type":"array","items":{"type":"string"},"description":"Target headcount ranges (enum values)."},"industry":{"type":"array","items":{"type":"string"},"description":"Target industries."},"seniority":{"type":"array","items":{"type":"string"},"description":"Target seniority levels (enum values)."},"additional_info":{"type":"string","description":"Additional free-text persona context."},"tag":{"type":"string","maxLength":255,"description":"Short free-form label you can set to recognise this persona in your own systems. Two personas of the same workspace cannot share a tag — reusing one returns 409."}}},"V2PersonaWriteResponse":{"type":"object","required":["data"],"properties":{"data":{"type":"object","required":["id"],"properties":{"id":{"type":"integer","description":"ID of the persona. This ID is specific to your environment.","example":1234}}},"warnings":{"type":"array","items":{"type":"string"},"description":"Advisory warnings about the submitted persona, e.g. a missing job_title/location or a location that could not be resolved to a country (account mapping will not run for it). Omitted when there is nothing to report. Never blocks the write — the persona above is already saved."}}},"V2Company":{"type":"object","nullable":true,"required":["id"],"properties":{"id":{"type":"integer","description":"Numeric SQL id of the company. Environment-specific, prod only, not portable across environments."},"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true}}},"V2CompanyDetail":{"type":"object","description":"Enrichment data for a company. All fields are nullable — a company that has not been enriched yet is returned with null enrichment fields.","properties":{"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true},"url":{"type":"string","nullable":true,"description":"The company's website."},"linkedin_url":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true,"description":"LinkedIn company handle (slug)."},"logo_url":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"locations":{"type":"array","description":"The company's known locations, HQ first. `is_hq` marks the headquarters; every other entry is a secondary location.","items":{"type":"object","properties":{"is_hq":{"type":"boolean","description":"True for the headquarters location."},"city":{"type":"string","nullable":true},"region":{"type":"string","nullable":true},"state":{"type":"string","nullable":true},"country":{"type":"string","nullable":true},"country_code":{"type":"string","nullable":true,"description":"ISO country code."},"postal_code":{"type":"string","nullable":true},"line1":{"type":"string","nullable":true,"description":"First line of the street address."},"line2":{"type":"string","nullable":true,"description":"Second line of the street address, if any."},"formatted_address":{"type":"string","nullable":true,"description":"The full address as a single formatted string."},"latitude":{"type":"number","nullable":true},"longitude":{"type":"number","nullable":true}}}},"number_of_employees":{"type":"integer","nullable":true},"employee_range":{"type":"string","nullable":true,"description":"Employee headcount range, e.g. \"51-200\"."},"founded_year":{"type":"integer","nullable":true},"industries":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true,"description":"A short summary of the company's activity."},"tagline":{"type":"string","nullable":true,"description":"The company's LinkedIn tagline — a short one-line headline, distinct from `activity_summary`. `null` when the company has no LinkedIn data, or LinkedIn has no tagline for it."},"pipeline_configs":{"type":"array","description":"Every pipeline configured for this company, including ones set to `disabled`. Empty only when a pipeline was never configured for this company.","items":{"type":"object","required":["pipeline_type","configuration"],"properties":{"pipeline_type":{"type":"string","enum":["account_mapping_and_content","google_news"],"description":"Which pipeline this entry configures."},"configuration":{"type":"string","enum":["account_mapping","account_mapping_and_content","disabled"],"description":"How much runs for this company: `account_mapping` (account mapping only), `account_mapping_and_content` (account mapping plus content), or `disabled` (turns the pipeline off)."}}}}}},"V2LeadDetail":{"type":"object","description":"A lead in the authenticated workspace, with its linked profile, a reference to its current company, and its LinkedIn work history. All fields are nullable — a lead with no linked profile, or with a profile that has no current company, is returned with those fields set to `null` rather than an error.","required":["id"],"properties":{"id":{"type":"integer","description":"The lead id, as returned by the signals endpoints. Always use the `lead_id` value from those responses — don't guess, hard-code, or reuse an id from another workspace."},"first_name":{"type":"string","nullable":true},"last_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true,"description":"LinkedIn profile handle (slug)."},"linkedin_headline":{"type":"string","nullable":true},"avatar_url":{"type":"string","nullable":true},"email":{"type":"string","nullable":true,"description":"The lead's email address, when known. `null` if not set."},"phone":{"type":"string","nullable":true,"description":"The lead's phone number, when known. `null` if not set."},"position":{"type":"string","nullable":true,"description":"The lead's job title."},"location":{"type":"string","nullable":true},"geo":{"type":"object","nullable":true,"description":"The lead's location as structured data. `location` above is the same location as a display string; `geo` breaks it down into city, region, country, and ISO country code. `null` when no structured location could be resolved for this lead — not an error.","properties":{"city":{"type":"string","nullable":true},"region":{"type":"string","nullable":true},"country":{"type":"string","nullable":true},"country_code":{"type":"string","nullable":true,"description":"ISO country code."}}},"company":{"type":"object","nullable":true,"description":"The lead's current company, when one can be resolved. `null` when the lead has no linked profile, no current company, or that company is not tracked in your workspace.","required":["id"],"properties":{"id":{"type":"integer","description":"This company's ID in your workspace. Always use the `id` returned here — don't guess, hard-code, or copy it from another workspace — then pass it to `GET /v2/companies/{id}` to fetch its full enrichment data."},"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true},"activity_summary":{"type":"string","nullable":true,"description":"A short summary of the company's activity."},"employee_range":{"type":"string","nullable":true,"description":"Employee headcount range, e.g. \"51-200\"."},"location":{"type":"string","nullable":true},"is_top_account":{"type":"boolean","description":"True when this company is one of your top accounts. Reflects your top-account list at the time of the request, so a lead's badge changes as your list changes."}}},"experiences":{"type":"array","nullable":true,"description":"The lead's work history, in the order it appears on their LinkedIn profile, including their current position. `null` when this data is not available for this lead (for example, profiles that were not sourced from LinkedIn); an empty array means the profile has no work history listed.","items":{"type":"object","description":"One entry in the work history. All fields are nullable — a position with incomplete details is still returned, never dropped.","required":["is_current"],"properties":{"title":{"type":"string","nullable":true,"description":"Job title held in this position."},"company_name":{"type":"string","nullable":true},"company_linkedin_url":{"type":"string","nullable":true,"description":"The employer's LinkedIn page, when known."},"location":{"type":"string","nullable":true},"start_date":{"type":"string","nullable":true,"format":"date-time","description":"When this position started."},"end_date":{"type":"string","nullable":true,"format":"date-time","description":"When this position ended. `null` for the current position or when the end date is unknown."},"is_current":{"type":"boolean","description":"Whether this is the lead's current position."}}}}}},"V2LeadsQueryBody":{"type":"object","description":"Filters for the leads list. All fields are optional — an empty body returns the first page of every lead in your workspace, most recent first.","properties":{"cursor":{"type":"string","description":"Opaque pagination token from the previous response (`meta.next_cursor`). Omit it for the first page. Keep the same `sort` and filters while paginating with it."},"limit":{"type":"integer","minimum":1,"maximum":100,"default":25,"description":"Number of items per page. Defaults to 25. Maximum: 100."},"date_from":{"type":"string","format":"date-time","description":"Only leads created on or after this date (ISO 8601)."},"date_to":{"type":"string","format":"date-time","description":"Only leads created on or before this date (ISO 8601)."},"sort":{"type":"string","enum":["created_at:asc","created_at:desc"],"default":"created_at:desc","description":"Sort order. Leads are sorted by creation date only — most recent first by default."},"countries":{"type":"array","items":{"type":"string","minLength":1},"maxItems":100,"description":"Only leads located in one of these countries. Combined with `cities` (a lead matches if it is in one of the countries OR one of the cities).","example":["France","Germany"]},"cities":{"type":"array","items":{"type":"object","required":["name","country"],"properties":{"name":{"type":"string","minLength":1},"country":{"type":"string","minLength":1}}},"maxItems":100,"description":"Only leads located in one of these cities. Each city is paired with its country so \"Paris, France\" and \"Paris, US\" stay distinct.","example":[{"name":"Paris","country":"France"}]},"company_id":{"type":"integer","minimum":1,"description":"Only leads whose current company is this company — pass the `company.id` returned on leads, or the `company_id` returned by the other v2 endpoints. When present, takes priority over the identifier filters below. An id that is not in your workspace returns an empty page."},"company_ids":{"type":"array","items":{"type":"integer","minimum":1},"maxItems":100,"description":"Only leads whose current company is one of these companies. Pass workspace company ids — the `id` from a lead's `company` block, or from `POST /v2/companies/query`. Merged with `company_id`. Ids not in your workspace are ignored."},"company_domain":{"type":"array","items":{"type":"string"},"maxItems":100,"description":"Only leads whose current company matches one of these website domains (e.g. `acme.com`). Maximum 100 values. See `company_id` for filter priority."},"company_linkedin_handle":{"type":"array","items":{"type":"string"},"maxItems":100,"description":"Only leads whose current company matches one of these LinkedIn handles (slugs). Maximum 100 values. See `company_id` for filter priority."},"company_linkedin_url":{"type":"array","items":{"type":"string"},"maxItems":100,"description":"Only leads whose current company matches one of these LinkedIn page URLs. Maximum 100 values. See `company_id` for filter priority."}}},"V2LeadListItem":{"allOf":[{"$ref":"#/components/schemas/V2LeadDetail"},{"type":"object","properties":{"created_at":{"type":"string","format":"date-time","nullable":true,"description":"When the lead was added to your workspace — the date the list is sorted on."}}}]},"V2CompanySearchResponse":{"type":"object","required":["data"],"properties":{"data":{"type":"array","items":{"type":"object","required":["id","name","domain","linkedin_handle"],"properties":{"id":{"type":"integer","description":"Workspace company id. Pass it as `company_ids` on `POST /v2/leads/query`, or as the path id on `GET /v2/companies/{id}`."},"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true},"linkedin_handle":{"type":"string","nullable":true}}}}}},"V2LeadsPaginatedResponse":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/V2LeadListItem"}},"meta":{"type":"object","required":["next_cursor","has_more","resolved_companies"],"properties":{"next_cursor":{"type":"string","nullable":true,"description":"Pass this token as `cursor` in the next request to fetch the following page. `null` when there is no next page."},"has_more":{"type":"boolean","description":"Whether more leads exist after this page."},"resolved_companies":{"type":"array","description":"Companies resolved from the company filter. Same semantics as in `V2ContentsPaginatedResponse`.","items":{"$ref":"#/components/schemas/V2ResolvedCompany"}}}}}},"V2ContentAuthor":{"type":"object","description":"Who posted, commented, or reacted — a person or a company page.","required":["type"],"properties":{"type":{"type":"string","enum":["profile","company"]},"full_name":{"type":"string","description":"Present when `type` is `profile`."},"headline":{"type":"string","nullable":true,"description":"Present when `type` is `profile`."},"company_name":{"type":"string","description":"Present when `type` is `company`."},"linkedin_url":{"type":"string"}}},"V2ContentMention":{"type":"object","properties":{"name":{"type":"string"},"linkedin_url":{"type":"string"}}},"V2ContentEmbeddedPost":{"type":"object","description":"The post a reaction was made on.","properties":{"post_id":{"type":"string"},"link":{"type":"string"},"text":{"type":"string"},"author":{"$ref":"#/components/schemas/V2ContentAuthor"}}},"V2ContentData":{"description":"What this content item is about. Shape depends on `content_type`; every field is\nincluded only when we could extract it, so treat all fields as optional.\n\n- LinkedIn posts (`linkedinPost`, `linkedinCompanyPost`): `post_id`, `original_post_id`\n  (set when this is a repost), `is_repost`, `link`, `text` (full text, never truncated),\n  `posted_at`, `engagement`, `author`, `mentions` (`{ profiles: [...], companies: [...] }`),\n  `images` (array of URLs).\n- LinkedIn comments (`linkedinComment`): `linkedin_id` (the comment's own LinkedIn id,\n  when we have it), `text`, `linkedin_url`, `posted_at`, `engagement`, `author`, and\n  `post_content_id` — the numeric id of the commented post in your contents (fetch it\n  via the Contents endpoints), `null` when that post is not among your contents.\n- `engagement` is the same flat shape for both posts and comments: `likes`, `comments`\n  (replies, for a comment), `shares` (posts only), and a per-reaction-type breakdown —\n  `praise`, `empathy`, `interest`, `appreciation` — whenever the source exposes it.\n- LinkedIn reactions (`linkedinReaction`): `reaction_type` (e.g. `LIKE`), `author`,\n  and `post` — the parent post being reacted to.\n- LinkedIn job postings (`linkedinJobPosting`): `linkedin_id`, `linkedin_url`, `title`, `min_salary`,\n  `max_salary` (a number or a free-text string such as `\"$100K/yr\"`, when disclosed),\n  `location`, `posted_at`, `description` (full text).\n- Every other content type: `text` when we have it, omitted otherwise.","type":"object","properties":{"linkedin_id":{"type":"string","description":"The item's own LinkedIn id (a comment or a job posting) — not to be confused with this content item's own `id` at the top level."},"post_id":{"type":"string"},"original_post_id":{"type":"string","nullable":true},"is_repost":{"type":"boolean"},"link":{"type":"string"},"text":{"type":"string"},"posted_at":{"type":"string","format":"date-time"},"reaction_type":{"type":"string"},"engagement":{"type":"object","description":"Same flat shape for posts and comments. `shares` is posts only; `comments` means comments on a post, or replies to a comment. The reaction breakdown (`praise`/`empathy`/`interest`/`appreciation`) is present whenever the source exposes it.","properties":{"likes":{"type":"integer"},"comments":{"type":"integer","description":"Number of comments on a post, or number of replies to a comment."},"shares":{"type":"integer","description":"Posts only."},"praise":{"type":"integer"},"empathy":{"type":"integer"},"interest":{"type":"integer"},"appreciation":{"type":"integer"}}},"author":{"$ref":"#/components/schemas/V2ContentAuthor"},"mentions":{"type":"object","properties":{"profiles":{"type":"array","items":{"$ref":"#/components/schemas/V2ContentMention"}},"companies":{"type":"array","items":{"$ref":"#/components/schemas/V2ContentMention"}}}},"images":{"type":"array","items":{"type":"string"}},"post":{"$ref":"#/components/schemas/V2ContentEmbeddedPost"},"post_content_id":{"type":"integer","nullable":true,"description":"Comments only — the id of the commented post in your contents, usable with the Contents endpoints. `null` when that post is not among your contents."},"linkedin_url":{"type":"string","description":"URL of the item on LinkedIn (comment or job posting)."},"title":{"type":"string","description":"Job posting title."},"min_salary":{"oneOf":[{"type":"number"},{"type":"string"}],"nullable":true,"description":"Minimum disclosed salary, when available."},"max_salary":{"oneOf":[{"type":"number"},{"type":"string"}],"nullable":true,"description":"Maximum disclosed salary, when available."},"location":{"type":"string","description":"Job posting location."},"description":{"type":"string","description":"Full job posting description."}}},"V2ContentItem":{"type":"object","required":["id","content_type","created_at","lead_id","company_id"],"properties":{"id":{"type":"integer","description":"Numeric SQL id of the content item. Environment-specific, prod only, not portable across environments."},"content_type":{"type":"string","description":"Content type."},"created_at":{"type":"string","format":"date-time","description":"When the content record was created."},"data":{"$ref":"#/components/schemas/V2ContentData"},"lead_id":{"type":"integer","nullable":true,"description":"Numeric SQL id of the lead who posted, commented, or reacted, when they are one of your leads. Environment-specific, prod only."},"company_id":{"type":"integer","nullable":true,"description":"The associated company's ID in Sillage. `null` when the company is not on your target account list."}}},"V2ContentsPaginatedResponse":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/V2ContentItem"}},"meta":{"type":"object","required":["pagination","resolved_companies"],"properties":{"pagination":{"$ref":"#/components/schemas/V2PaginationMeta"},"resolved_companies":{"type":"array","description":"Companies resolved from the company filter (`company_id`, `company_domain`, `company_linkedin_handle`, or `company_linkedin_url`). Empty when no company filter was supplied. Each entry reflects the winning tier for this request.","items":{"$ref":"#/components/schemas/V2ResolvedCompany"}}}}}},"V2ContentRequestItem":{"type":"object","required":["id","type","stage","failed_reason","created_at","updated_at"],"properties":{"id":{"type":"integer","description":"Numeric SQL id of the content request. Environment-specific, prod only, not portable across environments."},"type":{"type":"string","enum":["account_mapping","top_account_content"],"description":"Request type."},"stage":{"type":"string","enum":["account_mapping_ready","account_mapping_in_progress","account_mapping_ingestion_ready","account_mapping_ingestion_in_progress","account_mapping_failed","completed","top_account_content_scraping_ready","top_account_content_scraping_starting","top_account_content_scraping_in_progress","top_account_content_failed"],"description":"Current processing stage."},"failed_reason":{"type":"string","nullable":true,"enum":["no_employee_resolved","persona_without_job_titles","missing_linkedin_target","request_timed_out","insufficient_credits","internal_error"],"description":"Why the request failed, when its stage is a failed stage. `null` for every request that has not failed. `no_employee_resolved`: no employee matching your persona was found for the company. `persona_without_job_titles`: your persona has no job title: add one to map accounts. `missing_linkedin_target`: the company had no usable LinkedIn page to work from. `request_timed_out`: the request took too long and was stopped. `insufficient_credits`: your workspace ran out of credits before the request could complete. `internal_error`: the request failed on our side — retry it, and contact support if it keeps failing."},"created_at":{"type":"string","format":"date-time","description":"When the request was created."},"updated_at":{"type":"string","format":"date-time","description":"When the request was last updated."},"company":{"$ref":"#/components/schemas/V2Company"},"inputs":{"description":"Request-type-specific input payload."}}},"V2ContentRequestsPaginatedResponse":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/V2ContentRequestItem"}},"meta":{"type":"object","required":["pagination","resolved_companies"],"properties":{"pagination":{"$ref":"#/components/schemas/V2PaginationMeta"},"resolved_companies":{"type":"array","description":"Companies resolved from the company filter. Same semantics as in `V2ContentsPaginatedResponse`.","items":{"$ref":"#/components/schemas/V2ResolvedCompany"}}}}}},"V2ContentRequestStatusItem":{"type":"object","required":["id","status","label","created_at","updated_at","company"],"description":"A single in-flight enrichment job, with its status and the company it is running for.","properties":{"id":{"type":"integer","description":"Numeric ID of the content request. This ID is specific to your environment."},"status":{"type":"string","enum":["pending","in_progress"],"description":"Normalized status of the request. `\"pending\"` means waiting to start; `\"in_progress\"` means actively processing. Failed and completed requests are excluded from this endpoint."},"label":{"type":"string","description":"Human-readable description of the current stage, safe to show to a user (e.g. \"Gathering content for your accounts\")."},"created_at":{"type":"string","format":"date-time","description":"When the request was created."},"updated_at":{"type":"string","format":"date-time","description":"When the request was last updated."},"company":{"type":"object","nullable":true,"required":["id","name","domain"],"description":"The company this request is running for. `null` for workspace-wide requests.","properties":{"id":{"type":"integer","description":"Numeric ID of the company. Specific to your environment."},"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true}}}}},"V2SignalRequestStatusItem":{"type":"object","required":["id","status","label","created_at","updated_at","scope","companies"],"description":"A single in-flight signal run, with its status and the accounts being scanned.","properties":{"id":{"type":"integer","description":"Numeric ID of the signal run. This ID is specific to your environment."},"status":{"type":"string","enum":["pending","in_progress"],"description":"Normalized status of the run. `\"pending\"` means waiting to start; `\"in_progress\"` means actively processing. Failed and completed runs are excluded from this endpoint."},"label":{"type":"string","description":"Human-readable description of the run's current stage, safe to show to a user (e.g. \"Detecting signals\")."},"created_at":{"type":"string","format":"date-time","description":"When the run was started."},"updated_at":{"type":"string","format":"date-time","description":"When the run was last updated."},"scope":{"type":"string","enum":["company","workspace"],"description":"`\"company\"` when the run targets specific accounts (companies array will be populated). `\"workspace\"` when it spans the whole workspace — companies will be empty, which is expected, not missing data."},"companies":{"type":"array","description":"The accounts being scanned in this run. Empty when `scope` is `\"workspace\"`.","items":{"type":"object","required":["id","name","domain"],"properties":{"id":{"type":"integer","description":"Numeric ID of the company. Specific to your environment."},"name":{"type":"string","nullable":true},"domain":{"type":"string","nullable":true}}}}}},"V2ResolvedCompany":{"type":"object","required":["company_id","matched_by","identifier"],"description":"A company matched from a company filter. All entries in a response share the same `matched_by` value (single winning tier per request).","properties":{"company_id":{"type":"integer","description":"The matched company's ID in Sillage."},"matched_by":{"type":"string","enum":["company_id","linkedin_handle","linkedin_url","domain"],"description":"Which identifier tier produced this match."},"identifier":{"type":"string","description":"The original identifier value supplied by the caller (domain, handle, URL, or numeric id echoed as a string)."}}},"V2ContentsQueryBody":{"type":"object","description":"POST body for `POST /v2/contents/query`. All fields are optional.","properties":{"page":{"type":"integer","minimum":1,"default":1,"description":"Page number (starts at 1). Defaults to 1."},"page_size":{"type":"integer","minimum":1,"maximum":100,"default":25,"description":"Number of items per page. Defaults to 25. Maximum: 100."},"date_from":{"type":"string","format":"date-time","description":"Filter contents created on or after this date (ISO 8601)."},"date_to":{"type":"string","format":"date-time","description":"Filter contents created on or before this date (ISO 8601)."},"content_type":{"type":"array","description":"Filter by content type. Native JSON array.","items":{"type":"string","enum":["linkedinComment","recentlyPromoted","linkedinPost","linkedinCompanyPost","linkedinJobPosting","webArticle","pressRelease","blogPost"]}},"company_id":{"type":"integer","minimum":1,"description":"Filter by the company's ID in Sillage. Takes priority over all human-identifier fields."},"company_domain":{"type":"array","minItems":1,"maxItems":100,"description":"Filter by company domain(s). Native JSON array. Maximum 100 values. Human identifiers are resolved to company IDs using a single-winning-tier waterfall: `company_id` > `company_linkedin_handle` > `company_linkedin_url` > `company_domain`. Only the highest-priority supplied tier is used; lower tiers are ignored. Multi-value = union within the winning tier.","items":{"type":"string","minLength":1}},"company_linkedin_handle":{"type":"array","minItems":1,"maxItems":100,"description":"Filter by company LinkedIn handle(s). Native JSON array. Maximum 100 values. See `company_domain` for tier priority.","items":{"type":"string","minLength":1}},"company_linkedin_url":{"type":"array","minItems":1,"maxItems":100,"description":"Filter by company LinkedIn URL(s). Native JSON array. Maximum 100 values. See `company_domain` for tier priority.","items":{"type":"string","minLength":1}},"lead_id":{"type":"integer","minimum":1,"description":"Filter for content authored by one lead. Use the `lead_id` shown on each content item, returned by the signals endpoints, or from the lead lookup endpoint."},"response_format":{"type":"string","enum":["concise","normalized","detailed"],"default":"normalized","description":"Controls how much detail the `data` field of each item includes. `normalized` (default): a clean, stable projection of the content. `concise`: `data` is omitted entirely. Lowest token footprint. `detailed`: deprecated alias of `normalized`, kept for backward compatibility."}}},"V2ContentRequestsQueryBody":{"type":"object","description":"POST body for `POST /v2/content-requests/query`. All fields are optional.","properties":{"page":{"type":"integer","minimum":1,"default":1,"description":"Page number (starts at 1). Defaults to 1."},"page_size":{"type":"integer","minimum":1,"maximum":100,"default":25,"description":"Number of items per page. Defaults to 25. Maximum: 100."},"date_from":{"type":"string","format":"date-time","description":"Filter by creation date on or after this date (ISO 8601)."},"date_to":{"type":"string","format":"date-time","description":"Filter by creation date on or before this date (ISO 8601)."},"type":{"type":"string","enum":["account_mapping","top_account_content"],"description":"Filter by request type."},"stage":{"type":"array","description":"Filter by stage. Defaults to all stages except `completed`. Native JSON array.","items":{"type":"string","enum":["account_mapping_ready","account_mapping_in_progress","account_mapping_ingestion_ready","account_mapping_ingestion_in_progress","account_mapping_failed","completed","top_account_content_mapping_in_progress","top_account_content_scraping_ready","top_account_content_scraping_starting","top_account_content_scraping_in_progress","top_account_content_failed"]}},"company_id":{"type":"integer","minimum":1,"description":"Filter by the company's ID in Sillage. Takes priority over all human-identifier fields."},"company_domain":{"type":"array","minItems":1,"maxItems":100,"description":"Filter by company domain(s). Native JSON array. Maximum 100 values. See `company_id` for tier priority.","items":{"type":"string","minLength":1}},"company_linkedin_handle":{"type":"array","minItems":1,"maxItems":100,"description":"Filter by company LinkedIn handle(s). Native JSON array. Maximum 100 values.","items":{"type":"string","minLength":1}},"company_linkedin_url":{"type":"array","minItems":1,"maxItems":100,"description":"Filter by company LinkedIn URL(s). Native JSON array. Maximum 100 values.","items":{"type":"string","minLength":1}}}},"V2EnrichedAccount":{"type":"object","required":["company","tier","imported_at"],"properties":{"id":{"type":"integer","description":"Identifier of the enriched account.","example":789},"company_id":{"type":"integer","description":"The company's ID in Sillage (same as `id`).","example":789},"company":{"type":"object","required":["status"],"properties":{"name":{"type":"string"},"domain":{"type":"string"},"linkedin_url":{"type":"string"},"linkedin_handle":{"type":"string"},"logo_url":{"type":"string"},"status":{"type":"string","enum":["found","not_found"]}}},"tier":{"type":"string","enum":["Tier 1","Tier 2","Tier 3"],"nullable":true,"description":"The account tier. `null` when no tier has been set."},"imported_at":{"type":"string","format":"date-time"}}},"V2SignalRunLaunchResponse":{"type":"array","description":"One element per detection run started. Keyword agents return one element; watchlist agents return one element per direction (inbound and outbound).","items":{"type":"object","required":["signal_request_id","stage"],"properties":{"signal_request_id":{"type":"integer","description":"ID of the created run. Use as `{id}` in the poll endpoint. This ID is specific to your environment."},"stage":{"type":"string","enum":["running"],"description":"Always `running` on a successful launch."}}}},"V2SignalRunPollResponse":{"type":"object","required":["signal_request_id","stage","metadata"],"properties":{"signal_request_id":{"type":"integer","description":"ID of the run."},"stage":{"type":"string","enum":["waiting","running","completed","completed_partial","failed"],"description":"Current stage of the signal run."},"metadata":{"type":"object","nullable":true,"required":["failed"],"description":"Extra details about a partially-covered run: the accounts that were not scanned. `null` when every account was scanned, or when the run failed entirely, in that case `stage` is `failed`.","properties":{"failed":{"type":"object","required":["dropped_account_ids"],"properties":{"dropped_account_ids":{"type":"array","items":{"type":"integer"},"description":"Accounts that were not scanned in this run. Retry the run to cover them. Each id is specific to your environment."}}}}}}},"V2PartnerCreditsByStatus":{"type":"object","description":"Credits grouped by billing lifecycle status. Keys: `held` (reserved for an action still in progress, not billable yet), `invoiceable` (completed, will appear on your next invoice), `invoice_edited` (an invoice covering these credits has been issued), `invoice_paid` (that invoice has been paid), `released` (the action did not complete; never billed). A key is only present when the period contains credits in that status.","additionalProperties":{"type":"number"}},"V2PartnerUsageResponse":{"type":"object","required":["workspaces","credits_by_status"],"properties":{"workspaces":{"type":"array","description":"One entry per workspace with consumption in the requested period.","items":{"type":"object","required":["id","credits_by_status","by_product"],"properties":{"id":{"type":"integer","description":"ID of the workspace. This ID is specific to your environment."},"credits_by_status":{"allOf":[{"$ref":"#/components/schemas/V2PartnerCreditsByStatus"}],"description":"Credits for this workspace in the period, grouped by lifecycle status."},"by_product":{"type":"array","description":"Consumption breakdown by product for this workspace.","items":{"type":"object","required":["product","credits_by_status"],"properties":{"product":{"type":"string","enum":["account_mapping_launch","content_profile","champion_enrichment","keyword_signal","competitor_signal","account_monitoring","discovery_essential","discovery_standard","discovery_advanced"]},"credits_by_status":{"$ref":"#/components/schemas/V2PartnerCreditsByStatus"}}}}}}},"credits_by_status":{"allOf":[{"$ref":"#/components/schemas/V2PartnerCreditsByStatus"}],"description":"Credits across every workspace in the period, grouped by lifecycle status."}}},"V2SignalAuthorProfile":{"type":"object","required":["type"],"description":"A person who published content.","properties":{"type":{"type":"string","enum":["profile"]},"full_name":{"type":"string","nullable":true},"headline":{"type":"string","nullable":true,"description":"LinkedIn headline of the person."},"linkedin_url":{"type":"string","nullable":true}}},"V2SignalAuthorCompany":{"type":"object","required":["type"],"description":"A company page that published content.","properties":{"type":{"type":"string","enum":["company"]},"company_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true}}},"V2KeywordDetectionData":{"type":"object","description":"Payload for `keywordDetection` signals: a post matching one of your tracked keywords.","properties":{"content_id":{"type":"integer","nullable":true,"description":"ID of the content the keyword matched in. Fetch the full post via the Contents endpoints."},"author":{"nullable":true,"description":"Who published the post — a person or a company page (discriminated by `type`). Null when the publisher is unknown.","oneOf":[{"$ref":"#/components/schemas/V2SignalAuthorProfile"},{"$ref":"#/components/schemas/V2SignalAuthorCompany"}]},"keywords_found":{"type":"array","items":{"type":"string"},"description":"The tracked keywords found in the post."}}},"V2WatchlistCommentAuthor":{"type":"object","description":"A person involved in a watchlist comment interaction.","properties":{"full_name":{"type":"string","nullable":true},"linkedin_url":{"type":"string","nullable":true},"headline":{"type":"string","nullable":true,"description":"LinkedIn headline of the person."}}},"V2WatchlistCommentData":{"type":"object","description":"Payload for watchlist comment signals (signal types ending in `InboundComment` or `OutboundComment`): a comment (`interaction`) left on a post (`post`). Each side carries a `content_id` usable with the Contents endpoints — null when no matching content exists in your workspace.","properties":{"interaction":{"type":"object","description":"The comment side of the interaction.","properties":{"type":{"type":"string","enum":["comment"]},"content_id":{"type":"integer","nullable":true},"author":{"$ref":"#/components/schemas/V2WatchlistCommentAuthor"}}},"post":{"type":"object","description":"The post the comment was left on.","properties":{"content_id":{"type":"integer","nullable":true},"author":{"$ref":"#/components/schemas/V2WatchlistCommentAuthor"}}}}},"V2JobUpdateData":{"type":"object","description":"Payload for `newJob` and `recentlyPromoted` signals: a person started a new position.","properties":{"previous_position":{"type":"object","description":"The role held before the change — fields are null when unknown.","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true}}},"new_position":{"type":"object","description":"The new role.","properties":{"role":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"start_date":{"type":"string","nullable":true,"description":"Start date as YYYY-MM-DD."}}}}},"V2DeepSearchData":{"type":"object","description":"Payload for `deepSearch` signals: a company event found on the web.","properties":{"title":{"type":"string","nullable":true},"tag":{"type":"string","nullable":true,"description":"Category of the event (e.g. funding)."},"date":{"type":"string","nullable":true},"sources":{"type":"array","nullable":true,"items":{"type":"object","properties":{"url":{"type":"string","nullable":true},"excerpts":{"type":"array","nullable":true,"items":{"type":"string"}}}}}}},"V2JobPostingData":{"type":"object","description":"Payload for `jobPosting`, `jobPostingInsight` and `jobPostingHiringManager` signals: an open role at a tracked company.","properties":{"posting":{"type":"object","nullable":true,"properties":{"title":{"type":"string","nullable":true},"company_name":{"type":"string","nullable":true},"job_url":{"type":"string","nullable":true},"location":{"type":"string","nullable":true},"description":{"type":"string","nullable":true},"published_at":{"type":"string","nullable":true}}},"job_title":{"type":"string","nullable":true}}},"V2SignalDetection":{"type":"object","required":["id"],"properties":{"id":{"type":"integer","description":"ID of the detection. Specific to your environment."},"signal_type":{"type":"string","nullable":true,"description":"Signal type, e.g. \"keywordDetection\"."},"data":{"nullable":true,"description":"Detection payload — the shape depends on `signal_type`:\n- `keywordDetection` → `V2KeywordDetectionData`\n- `*InboundComment` / `*OutboundComment` (watchlist) → `V2WatchlistCommentData`\n- `newJob`, `recentlyPromoted` → `V2JobUpdateData`\n- `deepSearch` → `V2DeepSearchData`\n- `jobPosting`, `jobPostingInsight`, `jobPostingHiringManager` → `V2JobPostingData`\n- `linkedinComment`, `linkedinReaction` → `CompetitorActivityData`\n- `jobPostingKeywordDetection` → `JobPostingKeywordDetectionData`\n- `championJobChange` → `ChampionTrackingData`","oneOf":[{"$ref":"#/components/schemas/V2KeywordDetectionData"},{"$ref":"#/components/schemas/V2WatchlistCommentData"},{"$ref":"#/components/schemas/V2JobUpdateData"},{"$ref":"#/components/schemas/V2DeepSearchData"},{"$ref":"#/components/schemas/V2JobPostingData"},{"$ref":"#/components/schemas/CompetitorActivityData"},{"$ref":"#/components/schemas/JobPostingKeywordDetectionData"},{"$ref":"#/components/schemas/ChampionTrackingData"}]},"detected_at":{"type":"string","format":"date-time","nullable":true,"description":"When the detection was created."},"signal_date":{"type":"string","format":"date-time","nullable":true,"description":"Date of the underlying signal event (e.g. post publish date)."},"lead_id":{"type":"integer","nullable":true,"description":"ID of the associated workspace lead. For detections without their own lead (e.g. keyword matches), this is the content author's lead when known. Null when the author is unknown."},"company_id":{"type":"integer","nullable":true,"description":"ID of the associated workspace company."},"agent_id":{"type":"integer","nullable":true,"description":"ID of the agent that produced this detection."}}},"V2SignalResponse":{"type":"object","required":["data"],"properties":{"data":{"$ref":"#/components/schemas/V2SignalDetection"}}},"V2SignalListResponse":{"type":"object","required":["data","meta"],"properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/V2SignalDetection"}},"meta":{"type":"object","required":["next_cursor","has_more"],"properties":{"next_cursor":{"type":"string","nullable":true,"description":"Opaque cursor to pass as `cursor` on the next request. Null when this is the last page."},"has_more":{"type":"boolean","description":"Whether more results exist beyond this page."}}}}},"V2SignalCountResponse":{"type":"object","required":["total"],"properties":{"total":{"type":"integer","description":"Total number of signal detections matching the supplied filters."}}},"V2SignalsQueryBody":{"type":"object","description":"POST body for `POST /v2/workspace/signals/query`. All fields are optional.","properties":{"cursor":{"type":"string","description":"Opaque pagination cursor. Pass the `next_cursor` value from the previous response to fetch the next page. Omit for the first page."},"limit":{"type":"integer","minimum":1,"maximum":100,"default":25,"description":"Number of items to return per page. Defaults to 25. Maximum: 100."},"signal_start_date":{"type":"string","format":"date-time","description":"Return detections whose signal date is on or after this timestamp (ISO 8601 with UTC offset). Defaults to 90 days before now. Cannot go further back than 180 days — an older value is clamped to that limit."},"signal_end_date":{"type":"string","format":"date-time","description":"Return detections whose signal date is on or before this timestamp (ISO 8601 with UTC offset)."},"detection_start_date":{"type":"string","format":"date-time","description":"Return detections that were first seen on or after this timestamp (ISO 8601 with UTC offset)."},"detection_end_date":{"type":"string","format":"date-time","description":"Return detections that were first seen on or before this timestamp (ISO 8601 with UTC offset)."},"agent_id":{"type":"integer","minimum":1,"description":"Return detections produced by a specific agent. Pass the numeric `agent_id` returned on each detection in the list response.","example":12},"signal_run_id":{"type":"integer","minimum":1,"description":"Return detections from a specific run. Pass the numeric run id returned by the signal-runs endpoint. Results are automatically scoped to your workspace."},"type":{"type":"array","minItems":1,"description":"Filter results to one or more signal types; unknown values are rejected.","items":{"type":"string","enum":["keywordDetection","newJob","recentlyPromoted","jobPostingKeywordDetection","competitorInboundComment","competitorOutboundComment","partnerInboundComment","partnerOutboundComment","customerInboundComment","customerOutboundComment","influencerInboundComment","influencerOutboundComment","championInboundComment","championOutboundComment","championJobChange","linkedinComment","linkedinReaction","jobPosting","jobPostingInsight","jobPostingHiringManager","deepSearch","leadLikedCompetitorContent","leadCommentedCompetitorContent","leadLikedOwnContent","leadCommentedOwnContent"]}},"company_id":{"type":"integer","minimum":1,"description":"Return detections for a specific company. Pass the numeric `company_id` returned in signal items — the same company ID used by `GET /v2/companies/{id}`. Taken at face value — no lookup is performed, so an ID that does not belong to your workspace returns an empty page rather than a `404`. Takes priority over all human-identifier fields below."},"company_domain":{"type":"array","minItems":1,"maxItems":100,"description":"Return detections for companies on your top-account list matching this domain. Native JSON array, maximum 100 values, OR filtering across multiple companies. See `company_id` for tier priority. Returns `404` when none of the supplied values resolve to a known company on your top-account list.","items":{"type":"string","minLength":1}},"company_linkedin_handle":{"type":"array","minItems":1,"maxItems":100,"description":"Return detections for companies on your top-account list matching this LinkedIn handle. Native JSON array, maximum 100 values. See `company_id` for tier priority. Returns `404` when none of the supplied values resolve to a known company on your top-account list.","items":{"type":"string","minLength":1}},"company_linkedin_url":{"type":"array","minItems":1,"maxItems":100,"description":"Return detections for companies on your top-account list matching this LinkedIn URL. Native JSON array, maximum 100 values. See `company_id` for tier priority. Returns `404` when none of the supplied values resolve to a known company on your top-account list.","items":{"type":"string","minLength":1}},"lead_id":{"type":"integer","minimum":1,"description":"Filter to signals linked to a specific lead. Use the `lead_id` returned by the signals endpoints; resolve details via `GET /v2/leads/{id}`. Only matches detections directly linked to the lead — not signals attributed to that lead through fallback matching."},"countries":{"type":"array","items":{"type":"string","minLength":1},"maxItems":100,"description":"Filter to signals whose linked lead is located in one of these countries. Combined with `cities`. Only matches signals directly linked to a lead — company-only signals are excluded.","example":["France"]},"cities":{"type":"array","items":{"type":"object","required":["name","country"],"properties":{"name":{"type":"string","minLength":1},"country":{"type":"string","minLength":1}}},"maxItems":100,"description":"Filter to signals whose linked lead is located in one of these cities (each paired with its country). Only matches signals directly linked to a lead.","example":[{"name":"Paris","country":"France"}]}}}}}}