Как в Конвертации Данных 2.1 настроить поиск последнего созданного элемента?

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

При настройке обмена данными между базами 1С через конфигурацию "Конвертация данных 2.1" часто возникает стандартная задача: сопоставить элементы справочников. Однако, что делать, если в базе-приемнике по заданным полям поиска (например, по наименованию или коду) находится не один, а несколько дублирующихся элементов? По умолчанию, система обмена сопоставит данные с первым найденным объектом, что может быть некорректно.

Рассмотрим ситуацию, когда нам необходимо найти не первый попавшийся, а самый последний созданный элемент. Это актуально, если в базе-приемнике есть реквизит с датой создания или датой изменения, по которому можно однозначно определить "свежесть" записи. В этой статье мы подробно разберем, как реализовать такой механизм поиска.

Решение через обработчик события "ПоляПоиска"

Наиболее правильным и производительным способом для реализации собственного алгоритма поиска является использование обработчика события ПоляПоиска в правиле конвертации объекта (ПКО). Этот обработчик позволяет полностью переопределить стандартный механизм поиска, заменив его своим кодом на языке 1С.

Проанализируем по шагам, как это настроить.

  1. Настройка полей поиска в ПКО.
    Сначала в конфигурации "Конвертация данных" откроем нужное правило конвертации объекта. На вкладке "Поля поиска" необходимо отметить галочками те поля, по которым будет выполняться поиск. Значения именно этих полей из объекта-источника будут переданы в наш обработчик.
  2. Создание обработчика события.
    Перейдем на вкладку "Обработчики событий" в том же ПКО. В списке доступных событий найдем ПоляПоиска и создадим для него новый обработчик. В открывшемся окне мы будем писать наш код.
  3. Написание кода для произвольного поиска.
    Логика кода в обработчике будет следующей: получить значения для поиска, выполнить собственный запрос к базе-приемнику с нужной сортировкой и вернуть найденную ссылку.

Рассмотрим подробнее сам код и его ключевые моменты. В обработчике нам доступны несколько важных параметров:

Посмотрим на пример. Допустим, мы переносим справочник "Контрагенты" и ищем его по ИНН. В базе-приемнике может быть несколько контрагентов с одинаковым ИНН, и нам нужен самый новый, определенный по реквизиту ДатаСоздания.

Код в обработчике ПоляПоиска может выглядеть так:


// Выполняем наш алгоритм только для первого варианта поиска
Если НомерВариантаПоиска = 1 Тогда

    // Получаем значение ИНН из входящих данных
    // Имя ключа "ИНН" должно совпадать с именем реквизита, 
    // по которому настроен поиск в ПКО.
    ИННДляПоиска = СвойстваПоиска["ИНН"];

    // Если ИНН не заполнен, то и искать нечего
    Если НЕ ЗначениеЗаполнено(ИННДляПоиска) Тогда
        СсылкаНаОбъект = Неопределено;
        Возврат;
    КонецЕсли;

    // Создаем и настраиваем запрос к базе-приемнику
    Запрос = Новый Запрос;
    Запрос.Текст = 
        "ВЫБРАТЬ ПЕРВЫЕ 1
        |    Контрагенты.Ссылка
        |ИЗ
        |    Справочник.Контрагенты КАК Контрагенты
        |ГДЕ
        |    Контрагенты.ИНН = &ИНН
        |
        |УПОРЯДОЧИТЬ ПО
        |    Контрагенты.ДатаСоздания УБЫВ"; // Ключевой момент: сортировка по дате в обратном порядке

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

КонецЕсли;

Анализ кода и важные нюансы

Давайте разберем, что именно делает этот код и на что стоит обратить внимание.

1. Конструкция ВЫБРАТЬ ПЕРВЫЕ 1.

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

2. Сортировка УПОРЯДОЧИТЬ ПО ... УБЫВ.

Это сердце нашего механизма. Мы сортируем все найденные по ИНН записи по реквизиту ДатаСоздания в убывающем порядке (УБЫВ — от англ. DESC). Таким образом, самая "свежая" запись всегда окажется на самом верху выборки. В связке с ПЕРВЫЕ 1 мы гарантированно получаем именно то, что нам нужно.

3. Установка параметра ПрекратитьПоиск = Истина.

Если вы забудете установить этот флаг, то после выполнения вашего кода "Конвертация данных" запустит свой стандартный механизм поиска. Это не только лишняя нагрузка на систему, но и может привести к тому, что ваш результат будет перезаписан результатом стандартного поиска. Поэтому, как только вы успешно нашли нужный объект, обязательно прекращайте дальнейший поиск.

4. Обработка ситуации, когда объект не найден.

Если запрос не вернул ни одной записи, мы оставляем параметр СсылкаНаОбъект равным Неопределено. В этом случае механизм обмена поймет, что сопоставлять не с чем, и создаст в базе-приемнике новый элемент. Параметр ПрекратитьПоиск в этом случае можно не устанавливать, но и вреда от его установки не будет.

Таким образом, использование обработчика ПоляПоиска дает нам полный контроль над процессом сопоставления объектов и позволяет реализовать практически любую, даже самую сложную бизнес-логику поиска, выходящую за рамки стандартных возможностей "Конвертации данных".

← На главную