{
  "openapi": "3.0.1",
  "info": {
    "title": "hh.ru Scraper (HeadHunter)",
    "description": "Scrape jobs from hh.ru and the HeadHunter network across Russia, Kazakhstan, Belarus, Uzbekistan, Kyrgyzstan, Georgia and Azerbaijan. Rich filters, full job descriptions, and incremental monitoring that emits only new or changed vacancies on recurring runs.",
    "version": "1.0",
    "x-build-id": "3RjHGjtp6RNHNou7L"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/trev0n~hh-ru-scraper/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-trev0n-hh-ru-scraper",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    },
    "/acts/trev0n~hh-ru-scraper/runs": {
      "post": {
        "operationId": "runs-sync-trev0n-hh-ru-scraper",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor and returns information about the initiated run in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/runsResponseSchema"
                }
              }
            }
          }
        }
      }
    },
    "/acts/trev0n~hh-ru-scraper/run-sync": {
      "post": {
        "operationId": "run-sync-trev0n-hh-ru-scraper",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "inputSchema": {
        "type": "object",
        "properties": {
          "query": {
            "title": "Search keywords",
            "type": "string",
            "description": "What to search for — Russian or English, e.g. <b>python</b> or <b>менеджер по продажам</b>. Leave empty to search by filters alone (for example every remote job in Moscow posted today)."
          },
          "excludeQuery": {
            "title": "Exclude keywords (server-side)",
            "type": "string",
            "description": "Vacancies containing these words are excluded by hh.ru itself before results are returned."
          },
          "startUrls": {
            "title": "Start URLs",
            "type": "array",
            "description": "Paste hh.ru search URLs or individual vacancy URLs. Build the search you want in your browser, copy the address, and drop it here — every filter in the link is honoured. Also accepts hh.kz, hh.uz, rabota.by, headhunter.kg, headhunter.ge and hh1.az links.",
            "items": {
              "type": "object",
              "required": [
                "url"
              ],
              "properties": {
                "url": {
                  "type": "string",
                  "title": "URL of a web page",
                  "format": "uri"
                }
              }
            }
          },
          "country": {
            "title": "Country",
            "enum": [
              "RU",
              "KZ",
              "BY",
              "UZ",
              "KG",
              "GE",
              "AZ",
              "OTHER"
            ],
            "type": "string",
            "description": "Restrict results to one country. Ukraine is absent on purpose — hh no longer operates there (the whole country returns four vacancies)."
          },
          "locations": {
            "title": "Cities / regions",
            "type": "array",
            "description": "City or region names, e.g. <b>Москва</b>, <b>Санкт-Петербург</b>, <b>Алматы</b>, <b>Ташкент</b>. English names work for countries. Anything that cannot be matched is reported in the log rather than silently ignored.",
            "items": {
              "type": "string"
            }
          },
          "areaIds": {
            "title": "Area IDs (advanced)",
            "type": "array",
            "description": "Numeric hh area IDs, if you already know them (1 = Moscow, 2 = Saint Petersburg, 40 = Kazakhstan).",
            "items": {
              "type": "string"
            }
          },
          "roleCategories": {
            "title": "Job categories",
            "type": "array",
            "description": "Professional-role categories from hh’s own catalogue. Each selection is expanded into the individual roles it contains.",
            "items": {
              "type": "string",
              "enum": [
                "19",
                "5",
                "15",
                "26",
                "8",
                "16",
                "14",
                "11",
                "24",
                "6",
                "23",
                "25",
                "1",
                "7",
                "17",
                "2",
                "9",
                "21",
                "4",
                "22",
                "18",
                "10",
                "20",
                "12",
                "3",
                "13",
                "27"
              ],
              "enumTitles": [
                "Автомобильный бизнес",
                "Административный персонал",
                "Безопасность",
                "Высший и средний менеджмент",
                "Добыча сырья",
                "Домашний, обслуживающий персонал",
                "Закупки",
                "Информационные технологии",
                "Искусство, развлечения, массмедиа",
                "Маркетинг, реклама, PR",
                "Медицина, фармацевтика",
                "Наука, образование",
                "Продажи, обслуживание клиентов",
                "Производство, сервисное обслуживание",
                "Рабочий персонал",
                "Розничная торговля",
                "Сельское хозяйство",
                "Спортивные клубы, фитнес, салоны красоты",
                "Стратегия, инвестиции, консалтинг",
                "Страхование",
                "Строительство, недвижимость",
                "Транспорт, логистика, перевозки",
                "Туризм, гостиницы, рестораны",
                "Управление персоналом, тренинги",
                "Финансы, бухгалтерия",
                "Юристы",
                "Другое"
              ]
            }
          },
          "roleIds": {
            "title": "Professional role IDs (advanced)",
            "type": "array",
            "description": "Individual hh professional-role IDs, or their Russian names (96 = Programmer / Developer).",
            "items": {
              "type": "string"
            }
          },
          "experience": {
            "title": "Required experience",
            "enum": [
              "noExperience",
              "between1And3",
              "between3And6",
              "moreThan6"
            ],
            "type": "string",
            "description": "Experience level demanded by the employer."
          },
          "employmentForm": {
            "title": "Employment type",
            "enum": [
              "FULL",
              "PART",
              "PROJECT",
              "FLY_IN_FLY_OUT"
            ],
            "type": "string",
            "description": "Full-time, part-time, project work or fly-in-fly-out (вахта)."
          },
          "workFormat": {
            "title": "Work format",
            "enum": [
              "ON_SITE",
              "REMOTE",
              "HYBRID",
              "FIELD_WORK"
            ],
            "type": "string",
            "description": "On site, remote, hybrid or field work."
          },
          "schedule": {
            "title": "Work schedule",
            "enum": [
              "fullDay",
              "shift",
              "flexible",
              "remote",
              "flyInFlyOut"
            ],
            "type": "string",
            "description": "Working-time arrangement."
          },
          "education": {
            "title": "Education required",
            "enum": [
              "not_required_or_not_specified",
              "higher",
              "special_secondary"
            ],
            "type": "string",
            "description": "Education level the employer asks for. Only these three values exist on the vacancy search — hh’s longer education list belongs to its CV search."
          },
          "searchFields": {
            "title": "Search only in",
            "type": "array",
            "description": "Restrict where the keywords are matched. By default hh searches everywhere; choosing \"Job title only\" makes results far more precise.",
            "items": {
              "type": "string",
              "enum": [
                "name",
                "company_name",
                "description"
              ],
              "enumTitles": [
                "Job title only",
                "Company name only",
                "Description only"
              ]
            }
          },
          "labels": {
            "title": "Special filters",
            "type": "array",
            "description": "Extra hh flags, e.g. accredited IT employer, salary stated, direct employer only.",
            "items": {
              "type": "string",
              "enum": [
                "with_address",
                "accept_handicapped",
                "not_from_agency",
                "accept_kids",
                "accredited_it",
                "low_performance",
                "internship",
                "night_shifts",
                "with_salary",
                "accept_teens",
                "accept_labor_contract"
              ],
              "enumTitles": [
                "Has an address",
                "Accessible to people with disabilities",
                "Direct employer (no agencies)",
                "Open to applicants aged 14+",
                "Accredited IT employer",
                "Few applicants so far",
                "Internship",
                "Night shifts",
                "Salary stated",
                "Open to teenagers",
                "Employment contract offered"
              ]
            }
          },
          "searchPeriod": {
            "title": "Posted within",
            "enum": [
              "0",
              "1",
              "3",
              "7",
              "30"
            ],
            "type": "string",
            "description": "Only vacancies published in the last N days. hh honours 1, 3, 7 and 30.",
            "default": "0"
          },
          "salary": {
            "title": "Minimum salary (hh-side)",
            "minimum": 0,
            "type": "integer",
            "description": "Ask hh for vacancies paying at least this much. Note that hh treats this softly — it keeps vacancies with no stated salary. Combine with \"Only with salary stated\" for a hard filter."
          },
          "currency": {
            "title": "Salary currency",
            "enum": [
              "RUR",
              "USD",
              "EUR",
              "KZT",
              "BYR",
              "UAH",
              "AZN",
              "GEL",
              "KGS",
              "UZS"
            ],
            "type": "string",
            "description": "Currency the minimum salary is expressed in.",
            "default": "RUR"
          },
          "onlyWithSalary": {
            "title": "Only vacancies with a stated salary",
            "type": "boolean",
            "description": "Drop the (very many) hh vacancies that hide their pay.",
            "default": false
          },
          "acceptTemporary": {
            "title": "Only vacancies accepting temporary work",
            "type": "boolean",
            "description": "Keep only vacancies whose employer accepts applicants looking for temporary work.",
            "default": false
          },
          "sortBy": {
            "title": "Sort by",
            "enum": [
              "relevance",
              "publication_time",
              "salary_desc",
              "salary_asc",
              "distance"
            ],
            "type": "string",
            "description": "Result ordering. Combine \"Newest first\" with \"Posted within\" to monitor fresh postings.",
            "default": "relevance"
          },
          "maxResults": {
            "title": "Maximum vacancies",
            "minimum": 0,
            "type": "integer",
            "description": "Stop after this many vacancies. 0 means no limit from us — but note hh itself never serves more than 2000 results for a single search, however deep you page. Split the search by city, category or date to go beyond that; the log says so explicitly when a search is capped.",
            "default": 100
          },
          "maxPages": {
            "title": "Maximum pages per search",
            "minimum": 0,
            "type": "integer",
            "description": "Extra safety stop. 0 means page until the results or the limit run out.",
            "default": 0
          },
          "pageSize": {
            "title": "Results per page",
            "minimum": 1,
            "maximum": 100,
            "type": "integer",
            "description": "100 is both the maximum and the cheapest — fewer requests for the same data.",
            "default": 100
          },
          "includeDetails": {
            "title": "Fetch full job descriptions",
            "type": "boolean",
            "description": "Open every vacancy to collect its full description and key-skills list. The listing pages do not contain the description at all, so this is the only way to get it — at the cost of one extra request per vacancy.",
            "default": false
          },
          "descriptionFormat": {
            "title": "Description format",
            "enum": [
              "text",
              "html"
            ],
            "type": "string",
            "description": "Only relevant when full descriptions are fetched.",
            "default": "text"
          },
          "descriptionMaxLength": {
            "title": "Truncate descriptions to N characters",
            "minimum": 0,
            "type": "integer",
            "description": "0 keeps them whole.",
            "default": 0
          },
          "detailConcurrency": {
            "title": "Parallel detail requests",
            "minimum": 1,
            "maximum": 10,
            "type": "integer",
            "description": "How many vacancies to open at once when fetching full descriptions. Leave it at 3 — hh.ru limits requests per address, so pushing this higher usually makes the run slower, not faster.",
            "default": 3
          },
          "includeKeywords": {
            "title": "Keep only vacancies containing (our side)",
            "type": "array",
            "description": "Applied after scraping, across title, company, description and key skills. Any match keeps it.",
            "items": {
              "type": "string"
            }
          },
          "excludeKeywords": {
            "title": "Drop vacancies containing (our side)",
            "type": "array",
            "description": "Applied after scraping. Any match drops the vacancy.",
            "items": {
              "type": "string"
            }
          },
          "minSalary": {
            "title": "Minimum salary (hard, our side)",
            "minimum": 0,
            "type": "integer",
            "description": "A strict filter we apply ourselves: vacancies with no stated salary, or paying less than this, are dropped. Use it when hh’s own soft salary filter keeps too much.",
            "default": 0
          },
          "maxAgeMinutes": {
            "title": "Maximum age in minutes",
            "minimum": 0,
            "type": "integer",
            "description": "Drop anything published longer ago than this. 0 disables. Useful for near-real-time monitoring.",
            "default": 0
          },
          "compact": {
            "title": "Compact output",
            "type": "boolean",
            "description": "Keep only the essential fields.",
            "default": false
          },
          "excludeEmptyFields": {
            "title": "Omit empty fields",
            "type": "boolean",
            "description": "Leave out fields that are empty for a given vacancy, producing smaller records.",
            "default": false
          },
          "incrementalMode": {
            "title": "Incremental monitoring",
            "type": "boolean",
            "description": "Remember what was seen on previous runs and emit only what changed — new, updated and reappeared vacancies. On a schedule this typically cuts output (and cost) by 80–95%, because a job board barely changes between runs.",
            "default": false
          },
          "stateKey": {
            "title": "Monitoring state key",
            "type": "string",
            "description": "Name for this monitor’s memory. Leave empty and one is derived from your search, so different searches never share a baseline. Set it explicitly to keep history when you tweak a search."
          },
          "emitUnchanged": {
            "title": "Also emit unchanged vacancies",
            "type": "boolean",
            "description": "Turns incremental mode into a full snapshot that is still tagged with what changed.",
            "default": false
          },
          "emitExpired": {
            "title": "Also emit vacancies that disappeared",
            "type": "boolean",
            "description": "Emit a record when a previously seen vacancy is gone — useful for tracking how fast roles close.",
            "default": false
          },
          "skipReposts": {
            "title": "Skip reposts",
            "type": "boolean",
            "description": "Employers often delete and re-post the same vacancy under a new ID. When enabled, a new vacancy whose content matches one that recently vanished is treated as a repost and dropped.",
            "default": false
          },
          "webhookUrl": {
            "title": "Webhook URL",
            "type": "string",
            "description": "POST the results as JSON to this URL after each run."
          },
          "telegramBotToken": {
            "title": "Telegram bot token",
            "type": "string",
            "description": "Token of the Telegram bot that should send you new matches."
          },
          "telegramChatId": {
            "title": "Telegram chat ID",
            "type": "string",
            "description": "The chat, group or channel the Telegram bot should post to."
          },
          "discordWebhookUrl": {
            "title": "Discord webhook URL",
            "type": "string",
            "description": "Post new matches into a Discord channel."
          },
          "slackWebhookUrl": {
            "title": "Slack webhook URL",
            "type": "string",
            "description": "Post new matches into a Slack channel."
          },
          "notificationLimit": {
            "title": "Vacancies per notification",
            "minimum": 1,
            "type": "integer",
            "description": "How many vacancies to list in one alert before summarising the rest as a count.",
            "default": 10
          },
          "notifyOnlyChanges": {
            "title": "Only notify when something changed",
            "type": "boolean",
            "description": "Stay quiet on runs that found nothing new, instead of sending an empty alert.",
            "default": true
          },
          "includeRunSummary": {
            "title": "Include run summary in notifications",
            "type": "boolean",
            "description": "Add the run totals (new, updated, expired) to each alert.",
            "default": true
          },
          "proxyConfiguration": {
            "title": "Proxy",
            "type": "object",
            "description": "Leave this on. hh.ru limits how many requests one address may make, so runs that share an address start getting refused — measured as only 1 of 6 simultaneous runs succeeding without a proxy, versus 5 of 6 with one. The default datacenter proxy is the cheap option and is what keeps scheduled and parallel runs reliable.",
            "default": {
              "useApifyProxy": true
            }
          }
        }
      },
      "runsResponseSchema": {
        "type": "object",
        "properties": {
          "data": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "actId": {
                "type": "string"
              },
              "userId": {
                "type": "string"
              },
              "startedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "finishedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "status": {
                "type": "string",
                "example": "READY"
              },
              "meta": {
                "type": "object",
                "properties": {
                  "origin": {
                    "type": "string",
                    "example": "API"
                  },
                  "userAgent": {
                    "type": "string"
                  }
                }
              },
              "stats": {
                "type": "object",
                "properties": {
                  "inputBodyLen": {
                    "type": "integer",
                    "example": 2000
                  },
                  "rebootCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "restartCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "resurrectCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "computeUnits": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "options": {
                "type": "object",
                "properties": {
                  "build": {
                    "type": "string",
                    "example": "latest"
                  },
                  "timeoutSecs": {
                    "type": "integer",
                    "example": 300
                  },
                  "memoryMbytes": {
                    "type": "integer",
                    "example": 1024
                  },
                  "diskMbytes": {
                    "type": "integer",
                    "example": 2048
                  }
                }
              },
              "buildId": {
                "type": "string"
              },
              "defaultKeyValueStoreId": {
                "type": "string"
              },
              "defaultDatasetId": {
                "type": "string"
              },
              "defaultRequestQueueId": {
                "type": "string"
              },
              "buildNumber": {
                "type": "string",
                "example": "1.0.0"
              },
              "containerUrl": {
                "type": "string"
              },
              "usage": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "integer",
                    "example": 1
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "usageTotalUsd": {
                "type": "number",
                "example": 0.00005
              },
              "usageUsd": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "number",
                    "example": 0.00005
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}