{
  "openapi": "3.0.1",
  "info": {
    "title": "HeadHunter (hh.ru) Jobs Scraper",
    "description": "Scrapes job vacancies with full descriptions from HeadHunter — the largest job site in Russia, Kazakhstan, Uzbekistan and Belarus. Keyword and region search with salary, experience, schedule and date filters, plus direct vacancy-URL lookup.",
    "version": "0.1",
    "x-build-id": "JEuNcjwJgWWENeu5l"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/scrapyx~hh-jobs-scraper/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-scrapyx-hh-jobs-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/scrapyx~hh-jobs-scraper/runs": {
      "post": {
        "operationId": "runs-sync-scrapyx-hh-jobs-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/scrapyx~hh-jobs-scraper/run-sync": {
      "post": {
        "operationId": "run-sync-scrapyx-hh-jobs-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": {
          "site": {
            "title": "Site",
            "enum": [
              "hh.ru",
              "hh.kz",
              "hh.uz",
              "rabota.by"
            ],
            "type": "string",
            "description": "Which regional HeadHunter portal to read. All four share one search index, so this does NOT restrict results to that country — it sets the site context (locale, currency, vacancy URLs). To actually filter by country or city, use Regions below.",
            "default": "hh.ru"
          },
          "keywords": {
            "title": "Search keywords",
            "type": "array",
            "description": "One search per entry — each keyword runs as its own query and gets its own SEARCH_SUMMARY row. Russian or English both work. Leave empty to browse every vacancy (optionally narrowed by Regions and the filters below).",
            "items": {
              "type": "string"
            }
          },
          "areas": {
            "title": "Regions (country or city)",
            "type": "array",
            "description": "Region ids to filter by, e.g. 113 = Russia, 1 = Moscow, 2 = Saint Petersburg, 40 = Kazakhstan, 160 = Almaty, 159 = Astana, 97 = Uzbekistan, 2759 = Tashkent, 16 = Belarus, 1002 = Minsk. A region name as HeadHunter spells it (e.g. Алматы) also works. Every value is checked against HeadHunter's own region dictionary before the run starts, and a query with an unknown region is refused rather than silently returning nationwide results.",
            "default": [],
            "items": {
              "type": "string"
            }
          },
          "vacancyUrls": {
            "title": "Vacancy URLs (direct mode)",
            "type": "array",
            "description": "Scrape specific vacancies directly, skipping search entirely. Accepts a full vacancy URL (https://hh.ru/vacancy/136131345) or a bare numeric vacancy id. Can be combined with a keyword search in the same run.",
            "default": [],
            "items": {
              "type": "string"
            }
          },
          "maxItemsPerQuery": {
            "title": "Max vacancies per search",
            "minimum": 0,
            "type": "integer",
            "description": "Stop paginating a query after this many vacancies. Set to 0 for unlimited — note that HeadHunter itself serves at most 2000 results per query no matter how many matches exist, so unlimited means 'up to 2000'. Narrow by region, period or keyword to reach the rest.",
            "default": 100
          },
          "includeVacancyDetails": {
            "title": "Fetch full vacancy descriptions",
            "type": "boolean",
            "description": "Fetch the complete ad (full HTML description, key skills, employer details, exact address, publication date) for every result via one extra request per vacancy. Turn this off for a fast listing-only crawl — search results already carry title, employer, salary, region, work schedule and the vacancy URL.",
            "default": true
          },
          "searchFields": {
            "title": "Search only in",
            "type": "array",
            "description": "Restrict where the keyword is matched. Leave empty to search everywhere.",
            "items": {
              "type": "string",
              "enum": [
                "name",
                "company_name",
                "description"
              ],
              "enumTitles": [
                "Vacancy title",
                "Company name",
                "Vacancy description"
              ]
            },
            "default": []
          },
          "experience": {
            "title": "Experience level",
            "enum": [
              "",
              "noExperience",
              "between1And3",
              "between3And6",
              "moreThan6"
            ],
            "type": "string",
            "description": "Required work experience.",
            "default": ""
          },
          "employment": {
            "title": "Employment type",
            "type": "array",
            "description": "Employment types to include. Leave empty for all.",
            "items": {
              "type": "string",
              "enum": [
                "full",
                "part",
                "project",
                "volunteer",
                "probation"
              ],
              "enumTitles": [
                "Full time",
                "Part time",
                "Project work",
                "Volunteering",
                "Internship"
              ]
            },
            "default": []
          },
          "schedule": {
            "title": "Work schedule",
            "type": "array",
            "description": "Work schedules to include, e.g. pick 'Remote' for remote-only. Leave empty for all.",
            "items": {
              "type": "string",
              "enum": [
                "fullDay",
                "shift",
                "flexible",
                "remote",
                "flyInFlyOut"
              ],
              "enumTitles": [
                "Full day",
                "Shift work",
                "Flexible",
                "Remote",
                "Rotational (fly-in fly-out)"
              ]
            },
            "default": []
          },
          "searchPeriod": {
            "title": "Posted within",
            "enum": [
              "",
              "1",
              "3",
              "7",
              "30"
            ],
            "type": "string",
            "description": "Only vacancies published in the last N days. Useful for scheduled runs that should pick up new postings only.",
            "default": ""
          },
          "onlyWithSalary": {
            "title": "Only vacancies with a stated salary",
            "type": "boolean",
            "description": "Skip ads that do not state pay.",
            "default": false
          },
          "salary": {
            "title": "Minimum salary",
            "minimum": 0,
            "type": "integer",
            "description": "Minimum salary in the site's own currency (RUB on hh.ru, KZT on hh.kz, UZS on hh.uz, BYN on rabota.by). Leave empty for no minimum."
          },
          "orderBy": {
            "title": "Sort by",
            "enum": [
              "",
              "relevance",
              "publication_time",
              "salary_desc",
              "salary_asc"
            ],
            "type": "string",
            "description": "Result ordering. 'Publication date' is the right choice for monitoring runs.",
            "default": ""
          },
          "maxConcurrency": {
            "title": "Max concurrent requests",
            "minimum": 1,
            "maximum": 16,
            "type": "integer",
            "description": "Upper bound on requests in flight at once, across search paging and vacancy-detail fetches. This is the main speed control here: hh pages are heavy (~2s each), so a run with details is dominated by request latency. Measured on 20 vacancies — 4 gave 13.0s, 8 gave 8.5s, and 12 gave no further gain while worsening the slowest requests. Lower it if you start seeing errors in the log.",
            "default": 8
          },
          "proxyConfiguration": {
            "title": "Proxy",
            "type": "object",
            "description": "Apify Proxy on the shared datacenter pool. This is the default because it is included in your plan at no extra cost and this target works through it. If you start seeing blocks, challenges or empty results, switch the group here to Residential -- it uses real consumer IPs and gets through more, but Apify bills residential traffic per gigabyte, so leave it off unless you need it.",
            "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
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}