Как в Конверсии данных 2.0 программно установить папку для новых элементов при загрузке

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

При настройке обмена данными между конфигурациями 1С с помощью инструмента «Конверсия данных 2.0» (КД 2.1) часто возникает задача: если объект (например, товар из справочника Номенклатура) не был найден в приемнике по полям поиска, его необходимо поместить в заранее определенную группу (папку). Это позволяет избежать «мусора» в корне справочника и упрощает дальнейшую ручную обработку новых данных бухгалтером или менеджером.

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

Разбор ошибки: почему обработчик «При загрузке» не подходит

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

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

Следовательно, следующий код не сработает:


Если ОбъектНайден = Ложь Тогда
    // Здесь переменная Объект еще не инициализирована (Неопределено)
    Объект.Родитель = Справочники.Номенклатура.НайтиПоНаименованию("ПАПКА");
КонецЕсли;

Попытка обратиться к свойству Родитель у значения Неопределено вызовет ошибку выполнения скрипта. Именно поэтому важно понимать последовательность событий при загрузке в КД 2.1.

Правильное решение: использование обработчика «После загрузки»

Проанализируем преимущества переноса логики в событие «После загрузки». На этом этапе:

  1. Объект уже либо найден в базе данных, либо создан как новый экземпляр в памяти (но еще не записан).
  2. Реквизиты, переданные из файла обмена, уже заполнены.
  3. Параметр ОбъектНайден по-прежнему доступен и корректно указывает, был ли объект найден (Истина) или создан (Ложь).

Таким образом, мы можем безопасно изменять свойства объекта. Рассмотрим пример кода, который решает поставленную задачу:


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

Важный нюанс: Обработчик «После загрузки» выполняется до записи объекта в базу данных. Это идеальное место для финальной корректировки реквизитов.

Оптимизация производительности при загрузке

Разберем ситуацию, когда в файле загрузки содержатся тысячи элементов. Если мы будем использовать метод НайтиПоНаименованию() в каждом ПКО для каждого нового объекта, это создаст колоссальную нагрузку на базу данных и существенно замедлит процесс загрузки. Посмотрим, как можно оптимизировать этот процесс.

Лучшая практика — найти ссылку на нужную папку один раз в самом начале загрузки и сохранить ее в глобальном параметре. Для этого выполним следующие шаги:

  1. В дереве конверсии перейдем в «Алгоритмы / Запросы» или воспользуемся обработчиком «Перед загрузкой данных» на уровне всей конверсии.
  2. Создадим параметр или используем структуру Параметры.

Пример кода в обработчике «Перед загрузкой данных» (выполняется 1 раз при старте):


ПапкаДляНовых = Справочники.Номенклатура.НайтиПоНаименованию("НОВЫЕ ПОСТУПЛЕНИЯ");
Если Не ПапкаДляНовых.Пустая() Тогда
    Параметры.Вставить("СсылкаНаПапкуДляНовых", ПапкаДляНовых);
КонецЕсли;

Теперь в ПКО Номенклатура в событии После загрузки код станет максимально легким и быстрым:


Если Не ОбъектНайден Тогда
    Если Параметры.Свойство("СсылкаНаПапкуДляНовых") Тогда
        Объект.Родитель = Параметры.СсылкаНаПапкуДляНовых;
    КонецЕсли;
КонецЕсли;

Дополнительные проверки и безопасность

Проанализируем еще несколько важных аспектов, которые стоит учитывать при программном изменении иерархии:

Резюме

Мы выяснили, что для решения задачи по программному определению папки для новых объектов в КД 2.0 необходимо использовать событие После загрузки. Попытки сделать это в событии При загрузке обречены на неудачу из-за особенностей инициализации переменной Объект. Для достижения максимальной скорости работы обмена рекомендуется кэшировать ссылку на целевую папку в структуре Параметры в начале сеанса загрузки.

← На главную