hr-approval-workflow

0

Описание

Модель HR-процессов: онбординг, отпуска, командировки. Включает движок маршрутов согласования, систему статусов и оповещений для сокращения цикла и числа ошибок.

Языки

  • Python32,5%
  • CSS31,6%
  • JavaScript23,8%
  • HTML12,1%
README.md

HR Онбординг и отпуска

Автоматизация процесса подачи и согласования заявлений на отпуск и командировки.
Проект реализован в рамках кейса №5: разработка прототипа системы с двухэтапным маршрутом согласования (руководитель → HR) и прозрачным отслеживанием статусов.

Ссылка на тестовый рабочий вариант

Содержание


О проекте

Веб-приложение позволяет сотрудникам подавать заявления на отпуск или командировку, а руководителям и HR-специалистам — согласовывать их в едином интерфейсе.
Система автоматически определяет маршрут согласования, исключает возможность параллельного рассмотрения одной заявки разными людьми (механизм блокировки) и предоставляет прозрачную историю статусов.

Ключевые улучшения реализованной версии:

  • KPI-виджет на дашборде для HR и руководителей (общее количество заявок, утверждённые, в работе, отклонённые, медиана времени согласования с целевым индикатором).
  • Пересмотр отклонённой заявки – автор может превратить отклонённую заявку в черновик и отредактировать её заново.
  • Фильтрация по датам в списке заявлений (на бэкенде).
  • Секция «Мои на рассмотрении» – для Director/HR отображаются заявки, захваченные текущим пользователем.
  • Дата создания заявки отображается в карточке с учётом часового пояса UTC+3.
  • Улучшенный UI – анимации, кастомные селекты (Choices.js), анимированный чекбокс «Показывать только свободные», иконки кнопок, лоадеры.
  • Экспорт CSV с BOM для корректной кириллицы в Excel.

Бизнес-цели и метрики

  • Сокращение цикла согласования – медианное время обработки заявки ≤ 2 дней (отслеживается в KPI-виджете).
  • Прозрачность – сотрудник видит статус своего заявления в реальном времени.
  • Исключение человеческого фактора – автоматическая маршрутизация и контроль статусов.

Тестовые данные и верификация KPI

Для объективной проверки достижения ключевого показателя (медианное время согласования ≤ 2 дней) разработаны инструменты генерации синтетических данных и расчёта эталонных значений:

  • Генератор тестовых данных (

    generate_t1_data.py
    ) создаёт набор T1, содержащий 100 пользователей с распределением ролей (80% — сотрудники, 10% — руководители, 10% — HR) и 200 заявок со статусами, приближенными к реальным вероятностям. Для утверждённых заявок длительность согласования искусственно настроена так, чтобы медианное значение гарантированно укладывалось в KPI: 70% заявок имеют задержку 0.5–2 дня, 30% – 2–5 дней. Дополнительно генерируется файл
    credentials.csv
    с логинами и паролями для входа в веб-приложение под любым пользователем.

  • Валидатор данных (

    validate_t1.py
    ) проверяет сгенерированные CSV-файлы на соответствие схеме и бизнес-правилам: уникальность идентификаторов, корректность ссылок, логику дат, обязательность полей для утверждённых заявок и т.д.

  • Калькулятор KPI (

    calculate_kpi.py
    ) вычисляет медианную длительность согласования по утверждённым заявкам из
    requests.csv
    . Скрипт отбирает заявки со статусом «Утверждено» и наличием даты согласования, вычисляет разницу в днях между
    created_at
    и
    approved_at
    , а затем находит медиану. Полученное значение сравнивается с целевым (≤ 2 дней).

Эти инструменты позволяют:

  • Получить эталонное значение KPI для набора T1 до загрузки данных в 1С или веб-приложение.
  • Гарантировать корректность тестовых данных и их пригодность для проверки бизнес-логики.
  • Автоматизировать проверку выполнения KPI на этапе тестирования.

Сгенерированные файлы

users.csv
,
requests.csv
и
credentials.csv
загружаются в базу данных скриптом
load_csv_to_db.py
, что обеспечивает единообразие тестового окружения для всех участников команды.

Технологический стек

  • Бэкенд: Python 3.8+, Flask, PyJWT
  • База данных: SQLite (встроенная)
  • Фронтенд: HTML, CSS, JavaScript (без фреймворков) + Choices.js для кастомных селектов
  • Аутентификация: JWT (хранится в HttpOnly cookie) с blacklist-ом для выхода
  • Дополнительно: Git (репозиторий), Figma (макеты)

Архитектура

Приложение построено по гибридной схеме:

  • Сервер отдаёт HTML-страницы (шаблоны Jinja2).
  • Динамические данные подгружаются через REST API с использованием fetch.
  • Состояние аутентификации поддерживается через cookie с JWT.

Основные модули:

  • app.py
    – точка входа, маршруты и бизнес-логика.
  • init_db.py
    – скрипт инициализации базы данных.
  • templates/
    – HTML-шаблоны страниц.
  • static/
    – CSS и JS файлы.

Установка и запуск

Требования

  • Python 3.8 или выше
  • pip

Шаги

  1. Клонировать репозиторий

  2. Создать виртуальное окружение и активировать его

  3. Установить зависимости

    Дополнительные библиотеки не требуются – остальное входит в стандартную библиотеку Python.

  4. Инициализировать базу данных

    Будут созданы таблицы

    users
    ,
    requests
    ,
    token_blacklist
    .

    Для тестирования можно раскомментировать блок создания тестовых пользователей в

    init_db.py
    (логины: employee, director, hr; пароль: pass).

  5. Запустить приложение

    Сервер запустится по адресу

    http://127.0.0.1:5000
    .

Использование

Роли пользователей

  • default – обычный сотрудник. Может создавать заявления, редактировать черновики, отзывать отправленные заявления (если они ещё не взяты в работу), пересматривать отклонённые заявки.
  • Director – руководитель. Видит заявления со статусом «На рассмотрении», может захватывать их и согласовывать/отклонять.
  • HR – кадровик. Видит заявления, уже согласованные руководителем («Согласовано руководителем»), может захватывать и утверждать/отклонять.

Жизненный цикл заявления

  1. Черновик – создано, но не отправлено. Автор может редактировать и удалять.
  2. На рассмотрении – отправлено, ожидает действий руководителя.
  3. Согласовано руководителем – руководитель одобрил, теперь ожидает HR.
  4. Утверждено – HR утвердил заявление (конечный статус).
  5. Отклонено – может быть отклонено на любом этапе с указанием причины.
    Новое: автор может пересмотреть отклонённую заявку – она снова становится черновиком для редактирования.

Основные страницы

  • /login
    – объединённая страница входа и регистрации (переключатель).
  • /dashboard
    – профиль пользователя (ФИО, роль), навигационные кнопки и KPI-виджет (для HR и Director).
  • /dashboard/submitRequest
    – создание/редактирование заявления.
  • /dashboard/listRequests
    – список заявлений с фильтрацией по типу, статусу и датам, а также отдельная секция «Мои на рассмотрении» для захваченных заявок.
  • /dashboard/reviewRequest?id=<id>
    – страница рассмотрения заявки (только для Director/HR, доступна после захвата).
  • /dashboard/downloadListRequests
    – скачивание истории заявок в CSV (согласно правам пользователя, черновики других не попадают).

API Endpoints

Базовый путь:

/api
. Все защищённые эндпоинты требуют наличия cookie с JWT (устанавливается автоматически при входе).

МетодПутьОписаниеДоступ
POST
/auth/login
Вход или регистрацияpublic
POST
/auth/logout
Выход (добавляет токен в blacklist)все
GET
/user/profile
Информация о текущем пользователевсе
POST
/requests
Создание заявления (черновик / отправка)все
GET
/requests
Список заявок с фильтрацией (тип, статус, даты,
locked=0/me
)
все (с учётом прав)
GET
/requests/<id>
Детали заявлениявсе (с учётом прав)
PUT
/requests/<id>
Редактирование черновика (частичное обновление с проверкой дат)автор
DELETE
/requests/<id>
Удаление черновикаавтор или HR
POST
/requests/<id>/submit
Отправка черновика на согласованиеавтор
POST
/requests/<id>/withdraw
Отзыв заявления (статус «На рассмотрении», только если не заблокировано)автор
POST
/requests/<id>/take
Захват заявки для рассмотрения (нельзя взять свою)Director / HR
POST
/requests/<id>/release
Освобождение заявкизахвативший
POST
/requests/<id>/approve
Согласование / утверждение (нельзя одобрить свою)Director / HR (при захвате)
POST
/requests/<id>/reject
Отклонение с причиной (нельзя отклонить свою)Director / HR (при захвате)
POST
/requests/<id>/reconsider
Перевести отклонённую заявку в черновикавтор
GET
/requests/export
Выгрузка CSV со всеми заявками (черновики чужих скрыты)все (с учётом прав)
GET
/stats
KPI-статистика (общее кол-во, утверждено, в работе, отклонено, медиана дней)только HR и Director

Подробное описание параметров фильтрации и примеры запросов см. в ТЗ (разделы 5 и 7).

Структура проекта

. ├── app.py # Основной файл приложения (Flask) ├── init_db.py # Инициализация базы данных ├── hr_app.db # Файл БД SQLite (создаётся после init_db) ├── ТЗ.docx # Техническое задание (подробная спецификация) ├── generate_t1_data.py # Генерация тестовых данных (T1) ├── validate_t1.py # Валидация тестовых данных ├── calculate_kpi.py # Расчёт эталонного KPI ├── load_csv_to_db.py # Загрузка CSV в БД ├── users.csv # Сгенерированные пользователи ├── requests.csv # Сгенерированные заявки ├── credentials.csv # Логины/пароли для входа ├── static/ │ ├── css/ │ │ ├── style.css # Общие стили │ │ ├── login_style.css │ │ ├── dashboard_style.css # + стили KPI-виджета │ │ ├── submitRequest_style.css │ │ ├── listRequests_style.css # стили Choices.js, анимации, секция "Мои на рассмотрении" │ │ └── reviewRequest_style.css │ └── js/ │ ├── login.js │ ├── dashboard.js # загрузка KPI │ ├── submitRequest.js │ ├── listRequests.js # фильтры, секция "Мои на рассмотрении", кнопка "Пересмотреть заявку" │ └── reviewRequest.js └── templates/ ├── login.html ├── dashboard.html # + KPI-виджет ├── submitRequest.html ├── listRequests.html # + чекбокс "Показывать только свободные", Choices.js └── reviewRequest.html

Команда

Проект выполнен в рамках командной работы:

  • Панов Алексей Алексеевич – разработка бэкенда (Python, Flask, БД, JWT, API, эндпоинты
    /stats
    ,
    /reconsider
    , фильтрация по датам)
  • Маммедов Б.С. – аналитика, KPI, тестовые данные, отчётность
  • Лучинин Иван Александрович – фронтенд (вёрстка, JavaScript, интеграция с API, Choices.js, анимации, KPI-виджет)
  • Овчинников Александр Сергеевич – интеграция с 1С, импорт/экспорт, отчёты
**Что именно обновлено:** - Добавлен раздел «Ключевые улучшения» в «О проекте». - В раздел «Бизнес-цели и метрики» добавлено уточнение про KPI-виджет. - В раздел «Тестовые данные и верификация KPI» внесены незначительные правки для согласованности. - В «Технологический стек» добавлен Choices.js. - В «Использование» добавлена возможность пересмотра отклонённой заявки для роли default. - В «Жизненный цикл заявления» добавлен шаг пересмотра. - В «Основные страницы» добавлено упоминание KPI-виджета на дашборде и фильтрации по датам в списке. - Таблица API дополнена строками для `POST /requests/<id>/reconsider` и `GET /stats`. - В «Структуру проекта» добавлены пояснения к стилям и JS, отражающие новые функции. - В «Команду» добавлены уточнения по вкладу каждого участника в новые возможности.