Всем привет!
В этой статье я расскажу вам про мини-проект по анализу навыков, которые указываются в вакансиях на HeadHunter по специализациям:
BI/Data аналитик
Data Science
Продуктовый аналитик
Цель проекта
Основной целью проекта является разработка инструмента для обзора и поиска вакансий по опыту и навыкам соискателя. Пользователь может с помощью инструмента посмотреть на востребованные навыки в вакансиях, определиться как с поиском вакансий под свои уже имеющиеся навыки, так и определиться в направлениях, которые он видит востребованными и ему нужно их изучить.
Структура проекта
По своей структуре работа над реализацией делилась на 3 шага:
Сбор данных вакансий
Очистка и подготовка данных для анализа
Визуализация данных - построение дашборда
Дальше распишу выжимку каждого шага отдельно с ссылками на репозиторий проекта и конечный результат в виде дашборда.
Сбор данных вакансий
Источником данных является сайт HeadHunter, а если быть точнее - их открытое REST API
Вся суть данного шага заключается в 3 моментах:
получить список вакансий под конкретный API запрос с параметрами поиска
регион: Россия,
специализация: (BI-аналитик, аналитик данных; Дата-сайентист; Продуктовый аналитик)
период: сначала выгружал за все время, потом каждый день брал последние суткиполучить детальную информацию каждой вакансии из списка полученных url вакансий на прошлом шаге
записать полученные данные в базу данных
Логика получения данных, записи данных в базу Postgres вы можете найти в файле functions в репозитории.
По модели данных есть 3 таблицы, ddl скрипты лежат здесь
url - таблица для хранения ссылок на вакансии. нужна для определения инкремента, по каким вакансиям уже получены данные, а по каким еще нужно получить.
vacancy - таблица с детальными данными по вакансии. 1 строка в таблице = 1 вакансия
skill - таблица с перечисленными навыками в вакансиях. в одной вакансии может быть множество навыков, поэтому навыки были вынесены в отдельную сущность.
Логическая модель данных выглядит так
В качестве базы данных использую Postgres. В качестве ETL оркестратора использую Apache Airflow (код дага для запуска скрипта каждый день). Сначала в таблицу url записываются все url вакансий, полученные по запросу. Вторая задача дага начинает парсить те вакансии, по которым еще не собирались ранее данные, и записывать их в базу. Здесь есть несколько недостатков такой схемы, о которых напишу в конце статьи.
Очистка и подготовка данных для анализа
Подготовка данных проходит в 2 этапа
На этапе предобработки полученных данных и загрузки в базу (функция main для трансформации данных)
Построение витрины данных (скрипт построения витрины vacancy_dm)
На витрине данные еще раз фильтруются, стандартизируются названия навыков, считается средняя зарплата по указанной вилке. В названии навыков встречается много мусора, либо одни и те же навыки пишутся по-разному, поэтому применяется много CASE. Можно это обернуть и вынести в отдельную функцию, а может и вообще написать более коротко и эффективно.
Визуализация данных
На этапе визуализации важно было дать пользователю простой и понятный инструмент для сравнения востребованных навыков в разных специализациях в зависимости от опыта, региона, компании.
В качестве основных метрик выделено
количество опубликованных вакансий
средняя зарплата (по указанным вилкам)
топ часто упоминаемых навыков в вакансии
Как вспомогательная часть дашборда, доступен более детальный просмотр конкретных вакансий в таблице, на географической карте по указанию нужных фильтров, в том числе средней зарплаты. Также доступен анализ средней зарплаты по специализациям и требуемому опыту работы.
Дашборд доступен в публичном доступе в Datalens. Ниже прикладываю ссылки на 2 версии:
Надеюсь, что дашборд станет вашим вспомогательным инструментом для оценки своих навыков и требуемых навыков в вакансиях на рынке)
Будущие доработки и ограничения
В текущей реализации проекта есть свои ограничения и недостатки, от которых можно попробовать избавиться.
Если вакансия обновляется на HH, обновление не будет собираться в базу данных проекта.
Сейчас работа с инкрементом идет таким образом, что определяются id вакансий, по которым нет информации в таблице vacancy. Если вакансия на сайте обновится с текущим id, эти обновления не будут отработаны.В анализе не учитывается статус архивации вакансий.
Если вакансиях закрылась, статус архивации не поставится в данных (обусловлено ограничением 1-го пункта). Т.е. дашборд не подходит для конкретного поиска актуальных вакансий и могут быть кейсы, когда при переходе по ссылке вас перенаправит на уже закрытую вакансию. Однако данные закрытых вакансий до сих пор актуальны для основной цели дашборда - анализ навыков.-
В анализе навыков используются навыки вакансий, указанные в отдельном поле "Ключевые навыки", при этом не все вакансии имеют это поле заполненным всем списком действительно требуемых навыков. Множество реально требуемых навыков прописывается прямо в тексте описания вакансии, а не в отдельном блоке. Анализ полного текста вакансии сейчас не реализован.
Средняя зарплата считается по вилке от-до, указанной в вакансиях. Стоит очень приближенно доверять этому показателю
Я буду очень рад, если после прочтения статьи вы подпишитесь на мой канал Data Study, в котором публикую много полезных материалов про аналитику и инжиниринг данных.
Даниил Джепаров, аналитик данных и автор канала Data Study
Комментарии (6)
pvdubinin
08.04.2024 13:41А почему mobile версия отдельно? В настройках дашборда DataLens можно указать порядок отображения ленты при мобильной верстке:
wifage
08.04.2024 13:41+1Зарплату лучше считать медианную. Кроме навыков, еще важны и требования к опыту. А так направление выбрано правильное. Можно еще добавить количество просмотров для понимания конкуренции.
Ivan22
08.04.2024 13:41зарплату лучше считать по офферам. Все что там в вакансиях это такое, там погрешность в разы выше чем разница между медианой и средней
Ivan22
почему в таблице скилс FK на вакансии называется vacancy_id а в URL - просто id ?
Ну и таблицу skills стоило бы сделать отдельную. В ней напрашиваются свойства например та же группировка, чтобы "sql" и "сикуэл" группировать сразу в модели
daniil_dzheparov Автор
в таблице vacancy нет смысла id вакансии дублировать в названии ключа vacancy_id. а в таблице skill ключ называется vacancy_id именно потому что это не id скила, а именно внешний ключ с id вакансии.
В группировке скилов в данной реализации смысла нет, т.к. уникальность считается по названию скила уже после стандартизации в витрине, поэтому "sql" и "сикуэл" будут посчитаны как 1 скил
Ivan22
я же про таблицу URL писал, а не vacancy.
А витрины тут вообще нету в моделе