Как исключить сотрудников из выборки 1С по дополнительному реквизиту

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

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

Проанализируем несколько способов решения этой задачи: от простого использования вложенных запросов до более производительных методов с использованием соединений и программных интерфейсов БСП.

Метод 1. Использование вложенного запроса в секции ГДЕ

Это наиболее прямолинейный способ, который часто выбирают начинающие разработчики. Суть метода заключается в том, чтобы выбрать все ссылки из справочника, а затем в условии ГДЕ отсечь те, которые попадают в список «исключений».

Разберем пример кода, предложенный в обсуждении:


ВЫБРАТЬ
    Сотрудники.Ссылка КАК Сотрудник
ИЗ
    Справочник.Сотрудники КАК Сотрудники
ГДЕ
    НЕ Сотрудники.Ссылка В (
        ВЫБРАТЬ
            СотрудникиДополнительныеРеквизиты.Ссылка
        ИЗ
            Справочник.Сотрудники.ДополнительныеРеквизиты КАК СотрудникиДополнительныеРеквизиты
        ГДЕ
            СотрудникиДополнительныеРеквизиты.Свойство = &СвойствоВидНаЖительство
            И СотрудникиДополнительныеРеквизиты.Значение = &ЗначениеВидНаЖительство
    )

В данном примере мы используем конструкцию НЕ Ссылка В (...). Подзапрос обращается к табличной части ДополнительныеРеквизиты. Важно помнить, что в подзапросе мы выбираем именно поле Ссылка (владельца табличной части), чтобы сравнение в основном запросе прошло корректно.

Метод 2. Оптимизация через ЛЕВОЕ СОЕДИНЕНИЕ

Проанализируем ситуацию с точки зрения производительности. На больших базах данных использование конструкции В (ВЫБРАТЬ...) может приводить к замедлению работы, так как СУБД не всегда эффективно строит план выполнения для таких запросов. Более «красивым» и быстрым решением считается использование ЛЕВОГО СОЕДИНЕНИЯ с последующей проверкой на NULL.

Рассмотрим, как переписать наш запрос:


ВЫБРАТЬ
    Сотрудники.Ссылка КАК Сотрудник
ИЗ
    Справочник.Сотрудники КАК Сотрудники
    ЛЕВОЕ СОЕДИНЕНИЕ Справочник.Сотрудники.ДополнительныеРеквизиты КАК ДопРеквизиты
    ПО Сотрудники.Ссылка = ДопРеквизиты.Ссылка
    И ДопРеквизиты.Свойство = &СвойствоВидНаЖительство
    И ДопРеквизиты.Значение = &ЗначениеВидНаЖительство
ГДЕ
    ДопРеквизиты.Ссылка ЕСТЬ NULL

Как работает этот механизм? Мы пытаемся «приклеить» к каждому сотруднику запись из его таблицы доп. реквизитов, которая соответствует нашему условию. Если у сотрудника нет такого реквизита, то поля присоединенной таблицы будут содержать NULL. Условие ГДЕ ДопРеквизиты.Ссылка ЕСТЬ NULL как раз и оставит в результате только тех сотрудников, по которым совпадений не найдено.

Нюансы выбора справочника: Сотрудники vs Физические лица

При работе с кадровыми данными в конфигурациях типа ЗУП 3.1 или ERP важно понимать разницу между объектами. Дополнительные реквизиты могут быть назначены как справочнику Сотрудники, так и справочнику ФизическиеЛица.

  1. Сотрудники: Реквизит привязан к конкретному трудовому договору. Если человек уволился и нанялся снова, у него будет новый элемент справочника «Сотрудники» и, возможно, пустой набор реквизитов.
  2. Физические лица: Реквизит привязан к человеку как к личности. «Вид на жительство» логичнее хранить именно здесь, так как это персональная характеристика человека, не зависящая от его текущей должности.

Если данные хранятся в ФизическиеЛица, в запросе нужно обращаться к табличной части Справочник.ФизическиеЛица.ДополнительныеРеквизиты и соединяться через поле Сотрудник.ФизЛицо.

Обработка имен свойств и «хардкода»

Выясним причину, по которой использование Свойство.Имя = "ИмяСвойства" (как предлагалось в сообщении 5) считается плохой практикой. В системе 1С «Имя» дополнительного реквизита — это строковый идентификатор. Если администратор в пользовательском режиме изменит настройки, код может перестать работать.

Рекомендуемый подход: передавать ссылку на свойство в параметрах запроса. Найти нужную ссылку можно программно при инициализации запроса:


СвойствоСсылка = ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.НайтиПоНаименованию("Вид на жительство (Сотрудники)");
Запрос.УстановитьПараметр("СвойствоВидНаЖительство", СвойствоСсылка);

Использование инструментов БСП

Если задача стоит не в рамках одного сложного запроса, а в коде при итерации по массиву, мы можем воспользоваться программным интерфейсом Библиотеки стандартных подсистем (БСП). Рассмотрим функцию модуля УправлениеСвойствами.

Хотя для выборки 10 000 сотрудников лучше использовать запрос, для проверки одного объекта это выглядит лаконично:


ЗначениеРеквизита = УправлениеСвойствами.ЗначениеСвойства(ОбъектСсылка, "ВидНаЖительство");
Если ЗначениеЗаполнено(ЗначениеРеквизита) Тогда
    // Исключаем сотрудника
КонецЕсли;

Подведение итогов

Мы проанализировали ситуацию исключения данных по дополнительным реквизитам. Основные выводы:

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

← На главную