Разработка в конфигурации «1С:Зарплата и управление персоналом 3.1» (ЗУП 3.1) существенно отличается от предыдущих версий. Это становится особенно заметным, если требуется перенести данные из УПП 1.3 в ЗУП 3.1 — привычные в прошлом методы работы с регистрами здесь не всегда применимы. Одной из наиболее частых задач является получение списка сотрудников, которые числятся в штате на определенную дату. Однако из-за регулярных изменений структуры регистров в новых релизах, прямые запросы к таблицам базы данных могут привести к неработоспособности кода после очередного обновления. Рассмотрим наиболее правильные и надежные способы решения этой задачи с использованием программного интерфейса (API) конфигурации.
Проанализируем ситуацию: многие начинающие разработчики пытаются получить данные через срез последних регистра сведений КадроваяИсторияСотрудников или напрямую из регистра ТекущиеКадровыеДанныеСотрудников. Разберем по шагам, почему это плохая практика:
Если нам необходимо получить готовую таблицу значений с данными сотрудников, наиболее эффективным методом будет использование экспортной функции КадровыйУчет.КадровыеДанныеСотрудников(). Этот метод позволяет получить массив нужных нам полей для списка сотрудников на конкретную дату.
Рассмотрим пример кода, который возвращает работающих сотрудников:
// Определяем массив сотрудников (или пустой массив для всех)
СписокСотрудников = Новый Массив;
// Если массив пустой, нужно будет отобрать сотрудников по организации позже
// Формируем список необходимых полей
Поля = Новый Массив;
Поля.Добавить("Сотрудник");
Поля.Добавить("ДатаУвольнения");
Поля.Добавить("Подразделение");
Поля.Добавить("Должность");
// Получаем таблицу данных на текущую дату
ДатаАктуальности = ТекущаяДата();
ТаблицаДанных = КадровыйУчет.КадровыеДанныеСотрудников(Истина, СписокСотрудников, Поля, ДатаАктуальности);
// Теперь отфильтруем таблицу, оставив только тех, кто не уволен
ПараметрыОтбора = Новый Структура;
Для Каждого Строка Из ТаблицаДанных Цикл
Если ЗначениеЗаполнено(Строка.ДатаУвольнения) И Строка.ДатаУвольнения <= ДатаАктуальности Тогда
// Сотрудник уже уволен
Продолжить;
КонецЕсли;
// Логика обработки работающего сотрудника
КонецЦикла;
Важный нюанс: первый параметр функции (ТолькоРаботающие) при значении Истина автоматически пытается отсечь тех, кто явно не является сотрудником, но для полной гарантии лучше проверять поле ДатаУвольнения вручную в цикле или запросе.
Если задача стоит внутри сложного запроса (например, в отчете или обработке заполнения документов), лучше всего использовать процедуру КадровыйУчет.СоздатьВТКадровыеДанныеСотрудников. Этот метод создает временную таблицу в менеджере временных таблиц, к которой потом можно привязаться основным запросом.
Выясним причину, почему этот метод считается эталонным: он позволяет выполнять фильтрацию на уровне СУБД, не выгружая тысячи строк в память сервера приложений.
Разберем по шагам реализацию запроса:
Запрос = Новый Запрос;
МенеджерВТ = Новый МенеджерВременныхТаблиц;
Запрос.МенеджерВременныхТаблиц = МенеджерВТ;
// Подготавливаем параметры для формирования ВТ
ПараметрыПостроения = КадровыйУчет.ПараметрыПостроенияВТКадровыеДанныеСотрудников();
ПараметрыПостроения.ДатаПериода = ТекущаяДата();
ПараметрыПостроения.Организация = Объект.Организация; // Ссылка на организацию
// Вызываем типовой механизм формирования таблицы
КадровыйУчет.СоздатьВТКадровыеДанныеСотрудников(Запрос.МенеджерВременныхТаблиц, Истина, ПараметрыПостроения);
// Теперь пишем свой запрос к созданной таблице ВТКадровыеДанныеСотрудников
Запрос.Текст =
"ВЫБРАТЬ
| КадровыеДанные.Сотрудник КАК Сотрудник,
| КадровыеДанные.Подразделение КАК Подразделение,
| КадровыеДанные.Должность КАК Должность
|ИЗ
| ВТКадровыеДанныеСотрудников КАК КадровыеДанные
|ГДЕ
| (КадровыеДанные.ДатаУвольнения = ДАТАВРЕМЯ(1, 1, 1)
| ИЛИ КадровыеДанные.ДатаУвольнения > &Период)";
Запрос.УстановитьПараметр("Период", ТекущаяДата());
РезультатЗапроса = Запрос.Выполнить();
Этот подход гарантирует, что даже если в будущем 1С изменит название регистра сведений с кадровой историей, ваш код продолжит работать, так как СоздатьВТКадровыеДанныеСотрудников будет обновлена самими разработчиками типовой конфигурации.
Проанализируем ситуацию подробнее. Иногда «работающими» называют тех, кто не просто числится в штате, но и фактически присутствует на рабочем месте (не находится в декрете, в длительном отпуске или на больничном). Юридически они сотрудники, но фактически не работают.
Для решения этой подзадачи нам потребуется регистр сведений ДанныеСостоянийСотрудников. Рассмотрим, как дополнить наш запрос:
КадровыеДанныеСотрудников добавьте в список полей "Состояние".ГДЕ КадровыеДанные.Состояние = ЗНАЧЕНИЕ(Перечисление.СостоянияСотрудника.Работа).Посмотрим на пример со справочником Сотрудники. В ЗУП 3.1 один и тот же человек может быть заведен в справочнике несколько раз (например, как основной работник и как внутренний совместитель). Если ваша цель — получить список уникальных физических лиц, необходимо использовать группировку по полю ФизическоеЛицо.
Также важно помнить о договорах ГПХ. Договорники отображаются в списке сотрудников, но не являются штатными работниками. Чтобы исключить их, при формировании данных через КадровыйУчет, обращайте внимание на поле ВидЗанятости. У штатных сотрудников оно всегда заполнено (Основное место работы или Совместительство), а у работающих только по договорам ГПХ — может быть пустым или иметь специфическое значение.
Подведем итог: для программного получения работающих сотрудников в ЗУП 3.1 всегда используйте методы общего модуля КадровыйУчет. Это обеспечит стабильность вашего решения и избавит от необходимости переписывать запросы при каждом обновлении программы.