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