При массовой обработке данных или регламентной корректировке документов часто возникает задача: перепровести или изменить объекты в одной информационной базе (например, в «1С:Бухгалтерии предприятия») так, чтобы они повторно не выгружались через план обмена в другие системы (например, в «1С:Управление торговлей»). Разберем по шагам, какими способами можно отключить регистрацию изменений, в чем заключаются ключевые нюансы перепроведения документов и какие типовые механизмы платформы «1С:Предприятие» для этого предназначены.
Первое, что часто приходит на ум разработчику при необходимости отключить проверки и авторегистрацию — установить свойство ОбменДанными.Загрузка в значение Истина. Однако проанализируем поведение платформы в этом режиме:
ОбменДанными.Загрузка = Истина предназначен для загрузки уже готовых данных в базу-приемник.ОбработкаПроведения.РежимЗаписиДокумента.Проведение с включенным свойством Загрузка = Истина, движения сформированы не будут.Таким образом, этот способ подходит исключительно для простой перезаписи без проведения. Если же требуется перепроведение с актуализацией проводок и регистров, необходимо использовать другие механизмы.
В платформе 1С у каждого объекта данных есть свойство ОбменДанными.Получатели, отвечающее за список узлов, для которых регистрируются изменения. Чтобы платформа автоматически не добавляла узлы планов обмена в этот список перед записью, отключим автозаполнение и очистим коллекцию получателей.
Посмотрим на пример кода при проведении документа:
ДокументОбъект = СсылкаНаДокумент.ПолучитьОбъект();
// Отключаем авторегистрацию изменений платформой
ДокументОбъект.ОбменДанными.Получатели.АвтоЗаполнение = Ложь;
ДокументОбъект.ОбменДанными.Получатели.Очистить();
// Записываем документ с проведением
ДокументОбъект.Записать(РежимЗаписиДокумента.Проведение);
Важный нюанс при проведении: когда документ формирует проводки или записи в регистрах сведений/накопления, платформенная авторегистрация может сработать для сформированных наборов записей. Если регистры включены в состав того же плана обмена, они встанут в очередь на отправку. Чтобы подавить авторегистрацию движений, перед записью документа аналогичным образом отключают автозаполнение у каждого набора записей в коллекции Движения документа:
Для Каждого НаборЗаписей Из ДокументОбъект.Движения Цикл
НаборЗаписей.ОбменДанными.Получатели.АвтоЗаполнение = Ложь;
НаборЗаписей.ОбменДанными.Получатели.Очистить();
КонецЦикла;
В типовых конфигурациях 1С (включая «Бухгалтерию предприятия» и «Управление торговлей») регистрация изменений часто управляется подписками на события библиотеки стандартных подсистем (БСП) или встроенных механизмов обмена. Для обхода программной регистрации в подписках предусмотрены специальные флаги в структуре ДополнительныеСвойства.
Объединим платформенное отключение автозаполнения и флаг типовой подсистемы:
ДокументОбъект = СсылкаНаДокумент.ПолучитьОбъект();
// Отключение программных подписок на регистрацию
ДокументОбъект.ДополнительныеСвойства.Вставить("ОтключитьМеханизмРегистрацииОбъектов", Истина);
// Отключение платформенного механизма авторегистрации
ДокументОбъект.ОбменДанными.Получатели.АвтоЗаполнение = Ложь;
ДокументОбъект.ОбменДанными.Получатели.Очистить();
ДокументОбъект.Записать(РежимЗаписиДокумента.Проведение);
Если конфигурация сильно доработана, подписки на события не реагируют на флаги или состав плана обмена регистрирует подчиненные регистры автоматически, наиболее надежным решением является явное удаление объекта из очереди обмена после его проведения.
Для этого воспользуемся методом менеджера планов обмена ПланыОбмена.УдалитьРегистрациюИзменений. Разберем реализацию:
// Перепроводим документ стандартно
ДокументОбъект = СсылкаНаДокумент.ПолучитьОбъект();
ДокументОбъект.Записать(РежимЗаписиДокумента.Проведение);
// Получаем узел или массив узлов, для которых нужно отменить регистрацию
// Если нужно удалить для конкретного плана обмена (например, ПоОрганизации):
ВыборкаУзлов = ПланыОбмена.ОбменУправлениеТорговлейБухгалтерияПредприятия.Выбрать();
Пока ВыборкаУзлов.Следующий() Цикл
УзелОбмена = ВыборкаУзлов.Ссылка;
Если УзелОбмена = ПланыОбмена.ОбменУправлениеТорговлейБухгалтерияПредприятия.ЭтотУзел() Тогда
Продолжить;
КонецЕсли;
// Удаляем регистрацию самого документа
ПланыОбмена.УдалитьРегистрациюИзменений(УзелОбмена, ДокументОбъект.Ссылка);
// При необходимости удаляем регистрацию наборов движений
Для Каждого НаборЗаписей Из ДокументОбъект.Движения Цикл
ПланыОбмена.УдалитьРегистрациюИзменений(УзелОбмена, НаборЗаписей);
КонецЦикла;
КонецЦикла;
Обратите внимание: вызов ПланыОбмена.УдалитьРегистрациюИзменений следует выполнять строго после того, как транзакция записи документа зафиксирована, чтобы избежать повторной регистрации в промежуточных обработчиках проведения.
Для гарантированного исключения документа из обмена при пакетной обработке рекомендуется:
Записать отключить автозаполнение свойства Получатели у документа и наборов его движений."ОтключитьМеханизмРегистрацииОбъектов" в ДополнительныеСвойства.ПланыОбмена.УдалитьРегистрациюИзменений после проведения.