Как в Конвертации данных 2.1 исключить выгрузку связанного объекта и заменить его пустой ссылкой

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

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

Метод 1. Использование поля "Выражение" в ПКС

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

Рассмотрим ситуацию: у нас есть Документ1, в котором есть реквизит СвязанныйДокумент. Мы хотим обнулить эту ссылку при выгрузке, если не соблюдено условие. Для этого выполним следующие шаги:

  1. Откроем Правила конвертации свойств (ПКС) для Документа1.
  2. Найдем строку реквизита СвязанныйДокумент.
  3. В колонке "Выражение" напишем программный код, который будет вычисляться платформой.

Посмотрим на пример кода в поле "Выражение":


Результат = ?(УсловиеВыгрузки(Источник.СвязанныйДокумент), Источник.СвязанныйДокумент, Неопределено);

Важный нюанс: если переменной Результат присвоить значение Неопределено, движок конвертации воспримет это как пустую ссылку нужного типа. В файл обмена не попадет Уникальный Идентификатор (GUID) связанного объекта, и в базе-приемнике после загрузки реквизит будет просто пуст. Это исключает появление "битых" ссылок.

Метод 2. Управление выгрузкой через обработчик "Перед выгрузкой" ПКС

Выясним, как добиться того же результата, если логика проверки слишком сложна для одной строки в "Выражении". Мы можем использовать обработчик "Перед выгрузкой" конкретного свойства (ПКС).

Рассмотрим алгоритм действий:

  1. В обработчике ПКС пропишем проверку условий.
  2. Если объект выгружать не нужно, установим значение переменной Значение в Неопределено или вызовем Отказ = Истина (но Отказ в ПКС может полностью пропустить свойство, что не всегда эквивалентно очистке).

Пример кода в обработчике ПКС "Перед выгрузкой":


// Проверяем наличие связанной платежки через структуру подчиненности
Если НужноСкрытьСвязь(Источник.Ссылка) Тогда
    Значение = Неопределено;
КонецЕсли;

В этом случае Значение = Неопределено гарантирует, что в XML-файл будет записано пустое значение. При этом сам объект Документ2 не будет инициирован к выгрузке по ссылке.

Метод 3. Использование системной переменной ТолькоВыгрузкаПоСсылке

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

В ПКО Документа2 в обработчике "Перед выгрузкой" можно написать:


Если ТолькоВыгрузкаПоСсылке И Не МоеУсловиеДляПолнойВыгрузки(Объект) Тогда
    Отказ = Истина;
КонецЕсли;

Однако здесь кроется ловушка, которую мы должны учитывать: если мы просто установим Отказ = Истина в ПКО, основной Документ1 все равно выгрузит в файл GUID этого объекта. В результате в приемнике мы получим "Объект не найден". Поэтому данный метод рекомендуется комбинировать с настройками поиска.

Метод 4. Настройка "Не создавать новый объект в приемнике"

Разберем вариант, когда нам нужно, чтобы ссылка сохранялась только в том случае, если объект уже существует в базе-приемнике. Если его там нет — ссылка должна остаться пустой (или битой, с последующей очисткой).

  1. В настройках ПКО для Документа2 установим флаг "Не создавать новый объект в приемнике, если он не найден".
  2. Это приведет к тому, что при загрузке 1С попытается найти объект по GUID или полям поиска. Если не найдет — просто ничего не запишет.

Чтобы в базе-приемнике не оставалось "битых" ссылок, проанализируем обработчик "После загрузки" в ПКО Документа1:


// Очищаем битые ссылки в реквизите
Если Документы.Документ2.НайтиПоСсылке(Объект.СвязанныйДокумент).Пустая() Тогда
    Объект.СвязанныйДокумент = Документы.Документ2.ПустаяСсылка();
КонецЕсли;

Внимание: этот метод менее производителен, так как требует дополнительных обращений к базе данных при загрузке каждого объекта.

Метод 5. Передача параметров через ИсходящиеДанные

Иногда решение о том, выгружать ли Документ2, принимается в момент обработки Документа1. Мы можем передать информацию об этом "вниз" по цепочке выгрузки через структуру ИсходящиеДанные.

  1. В ПКС Документа1 (свойство СвязанныйДокумент) пишем: ИсходящиеДанные = Новый Структура("ПолнаяВыгрузка", Ложь);
  2. В ПКО Документа2 в обработчике "Перед выгрузкой" анализируем эти данные (они попадут во ВходящиеДанные):
    
    Если ВходящиеДанные <> Неопределено И ВходящиеДанные.ПолнаяВыгрузка = Ложь Тогда
        Отказ = Истина;
    КонецЕсли;
    

Этот способ позволяет гибко управлять логикой выгрузки в зависимости от контекста "родительского" объекта.

Почему ручная регистрация не всегда помогает?

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

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

← На главную