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