Как правильно рассчитать время нахождения сотрудника на работе по данным СКУД в 1С?

Программист 1С v8.3 (Управляемые формы) Управленческий учет
← На главную

Расчет рабочего времени на основе данных системы контроля и управления доступом (СКУД) — классическая задача для автоматизации управленческого учета. Часто данные из турникетов поступают в 1С в виде «сырого» лога событий: сотрудник, время, тип события (Вход/Выход). Основная сложность заключается не в простом вычитании времени, а в обработке ошибочных ситуаций, когда сотрудники проходят «паровозиком», забывают карты или совершают несколько входов подряд. В этой статье мы разберем методики очистки данных и программные способы расчета интервалов.

Анализ исходных данных и подготовка к расчету

Прежде чем приступать к написанию кода, проанализируем структуру данных. Обычно мы имеем дело с последовательностью записей. Рассмотрим типичную ситуацию: сотрудник может входить и выходить из здания несколько раз за день (на обед, по рабочим вопросам или на перекур). Наша задача — превратить этот плоский список в набор интервалов «Приход — Выход».

Разберем основные этапы предобработки, которые необходимо выполнить, чтобы расчет был корректным:

  1. Сортировка: Все данные должны быть строго отсортированы по сотруднику, а затем по дате и времени события. Без этого невозможно определить последовательность действий.
  2. Удаление дублей и ошибок: Часто возникают ситуации «Вход — Вход» или «Выход — Выход». Это может произойти, если турникет сработал дважды или сотрудник приложил карту, но не прошел, а затем воспользовался другим турникетом.
  3. Обработка граничных условий: Что делать, если первое событие за день — «Выход»? Вероятно, сотрудник остался с ночной смены. Если последнее событие — «Вход», значит, сотрудник еще не покинул здание.

Алгоритм очистки данных («схлопывание» событий)

Проанализируем ситуацию с ошибочными записями. Чтобы расчет не «поплыл», мы должны применить логический фильтр. Рассмотрим шаги по очистке лога:

Во-первых, удалим идущие подряд одинаковые события для одного сотрудника. Если у нас есть цепочка «Вход 09:00, Вход 09:05, Выход 18:00», мы должны оставить только самый первый «Вход». Если же цепочка «Вход 09:00, Выход 17:55, Выход 18:00», мы оставляем только последний «Выход».

Во-вторых, разберем методику обработки «сиротских» записей. Если рабочий день начинается с выхода, это событие зачастую игнорируется при расчете текущего дня (или относится к предыдущему, если система поддерживает учет ночных смен). Аналогично, незакрытый вход в конце дня требует либо ручного вмешательства, либо автоматического «закрытия» по графику (например, в 18:00 или в 21:00).

Реализация расчета в 1С: Запросы и временные таблицы

Посмотрим, как можно реализовать этот алгоритм в коде 1С. Использование обычного перебора выборки в цикле может быть неэффективным при больших объемах данных (тысячи сотрудников). Проанализируем, как решить задачу с помощью механизмов платформы.

Наиболее эффективный современный способ (для платформы 8.3.15 и выше) — использование оконных функций в языке запросов. Рассмотрим логику применения функций LEAD или LAG. Эти функции позволяют в текущей строке запроса «заглянуть» в следующую или предыдущую строку. Таким образом, для каждой строки с типом «Приход» мы можем сразу получить время следующего за ним «Выхода».

Если же мы работаем на более старых версиях платформы, воспользуемся классическим методом соединения временных таблиц:

  1. Поместим все события в ВременнаяТаблицаСобытий с порядковым номером (используя автоинкремент или соединение по условию «меньше»).
  2. Соединим таблицу саму с собой по условию: Т1.Сотрудник = Т2.Сотрудник И Т1.Номер = Т2.Номер - 1.
  3. Отфильтруем записи, где в Т1 событие — «Вход», а в Т2 — «Выход».

Пример структуры запроса для вычисления интервалов:


ВЫБРАТЬ
    Т1.Сотрудник,
    Т1.Период КАК ВремяВхода,
    МИНИМУМ(Т2.Период) КАК ВремяВыхода
ИЗ
    РегистрСведений.СобытияСКУД КАК Т1
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.СобытияСКУД КАК Т2
    ПО Т1.Сотрудник = Т2.Сотрудник
    И Т2.Период > Т1.Период
    И Т2.ВидСобытия = ЗНАЧЕНИЕ(Перечисление.ВидыСобытийСКУД.Выход)
ГДЕ
    Т1.ВидСобытия = ЗНАЧЕНИЕ(Перечисление.ВидыСобытийСКУД.Вход)
СГРУППИРОВАТЬ ПО
    Т1.Сотрудник, Т1.Период

Важно помнить, что такое простое соединение может работать долго на больших базах. Поэтому предварительно стоит ограничить выборку конкретным днем и списком сотрудников.

Методики расчета общего времени

Выясним, как именно суммировать полученные интервалы. Существует несколько подходов, выбор которых зависит от политики компании:

1. Метод «Чистое время»: Мы суммируем все интервалы нахождения внутри здания. Если сотрудник выходил курить 10 раз по 5 минут, эти 50 минут будут вычтены из рабочего времени. Это самый жесткий и точный метод.

2. Метод «Первый — последний»: Время рассчитывается как разница между самым первым входом и самым последним выходом за день. Промежуточные выходы игнорируются. Чтобы сотрудники не злоупотребляли этим, часто вводится фиксированный вычет на обед (например, 1 час), если общее нахождение превысило определенный порог.

3. Метод «С округлением и границами»: Проанализируем ситуацию, когда сотрудник приходит в 08:30 при начале рабочего дня в 09:00. В учетных системах часто настраивается «отсечение»: всё, что до 09:00 — личное время, если нет распоряжения о сверхурочных. Аналогично с уходом: уход в 18:05 считается как работа до 18:00.

Особые случаи: зоны и анти-реверс

Разберем подробнее технические нюансы работы самих систем СКУД. Рассмотрим понятие «Зоны доступа». В продвинутых системах офис разделен на зоны: «Улица», «Офис», «Столовая», «Склад». В этом случае выход из зоны «Офис» в зону «Столовая» может не считаться прерыванием рабочего времени, а выход в зону «Улица» — считаться.

Также стоит учитывать аппаратную функцию Anti-passback (антивозврат). Если она включена на стороне контроллера турникета, то сотрудник не сможет войти второй раз, не совершив выход. Это значительно упрощает жизнь программисту 1С, так как «сырые» данные приходят уже очищенными от большинства логических ошибок («вход после входа» становится невозможным).

Интеграция с табелем учета рабочего времени

Выясним юридический статус данных СКУД. Важно понимать, что данные с турникета — это лишь основание для заполнения ТабеляУчетаРабочегоВремени. Согласно трудовому законодательству, время нахождения в здании не всегда равно времени выполнения трудовых обязанностей. Поэтому в 1С рекомендуется делать промежуточный документ «Данные о присутствии», который HR-менеджер может скорректировать вручную (например, если сотрудник был в командировке или забыл карту), и только на его основе формировать окончательный табель.

Рассмотрим пример функции для расчета разницы в часах между двумя датами:


Функция РассчитатьВремяВЧасах(ВремяВхода, ВремяВыхода)
    Если ЗначениеЗаполнено(ВремяВхода) И ЗначениеЗаполнено(ВремяВыхода) Тогда
        РазницаВСекундах = ВремяВыхода - ВремяВхода;
        Возврат РазницаВСекундах / 3600;
    Иначе
        Возврат 0;
    КонецЕсли;
КонецФункции

Подводя итог, можно сказать, что идеальный расчет рабочего времени по СКУД в 1С — это сочетание автоматизированного сбора данных, сложного алгоритма очистки «мусора» и возможности ручной корректировки ответственными лицами.

← На главную