Как отладить перезаполнение учетных данных в инвентаризации и найти вызываемую процедуру в 1С

Программист 1С v8.3 (Управляемые формы) 1C:Бухгалтерия Бухгалтерский учет Сфера услуг, туризм и социальный сектор
← На главную

При работе с типовыми и отраслевыми решениями 1С:Предприятие (например, 1С:Бухгалтерия предприятия 3.0 или 1С:Общепит) разработчики и администраторы часто сталкиваются с ситуацией, когда кнопка "Перезаполнить учетные количества и суммы" в документе Инвентаризация товаров на складе ведет себя не так, как ожидается: вместо обновления колонок учетных остатков она полностью очищает табличную часть и удаляет позиции, добавленные вручную.

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

Шаг 1. Отслеживание асинхронных вызовов и обработчиков оповещений

Проанализируем исходный код команды формы. В современных конфигурациях на управляемых формах взаимодействие с пользователем происходит асинхронно через описания оповещений:


Процедура ПерезаполнитьУчетныеДанные(Команда)
    
    Если Объект.Товары.Количество() = 0 Тогда
        Возврат;
    КонецЕсли;
    
    ТекстВопроса = НСтр("ru = 'Перезаполнить учетные количества и суммы? %ПредупреждениеОЗаписиДокумента%'");
    ТекстВопроса = СтрЗаменить(ТекстВопроса, "%ПредупреждениеОЗаписиДокумента%", 
        ?(Модифицированность, Символы.ПС + НСтр("ru='(Перед заполнением документ будет записан!)'"), 
        ""));
    Оповещение = Новый ОписаниеОповещения("ВопросПерезаполнитьУчетныеДанныеЗавершение", ЭтотОбъект);
    ПоказатьВопрос(Оповещение, ТекстВопроса, РежимДиалогаВопрос.ДаНет, , КодВозвратаДиалога.Да, Заголовок);
    
КонецПроцедуры

Когда вы видите конструкцию Новый ОписаниеОповещения("ВопросПерезаполнитьУчетныеДанныеЗавершение", ЭтотОбъект), это значит, что при ответе пользователя на диалоговое окно платформа вызовет процедуру с именем ВопросПерезаполнитьУчетныеДанныеЗавершение, которая расположена в этом же модуле формы (так как второй параметр — ЭтотОбъект).

Найдем указанную процедуру в модуле формы. Внутри нее обычно находится обращение к серверу для запуска процедуры заполнения:


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

Шаг 2. Подключение к фоновому заданию для отладки на сервере

Очень часто длительные операции заполнения документов выносятся в фоновые задания с помощью общей библиотеки БСП. В коде это выглядит следующим образом:


Задание = ДлительныеОперации.ЗапуститьФоновоеЗаданиеСКонтекстомКлиента(ИмяЭкспортнойПроцедуры,
            ПараметрыЭкспортнойПроцедуры, КлючЗадания, НаименованиеЗадания);

Если установить точку останова в вызываемой серверной процедуре (например, Документы.ИнвентаризацияТоваровНаСкладе.ЗаполнитьПоОстаткам), отладчик не остановится на ней по умолчанию, так как код выполняется в отдельном фоновом сеансе на сервере.

Для решения этой проблемы и перехвата выполнения кода настроим автоматическое подключение отладчика:

  1. В Конфигураторе 1С перейдем в главное меню Отладка — Подключение...
  2. В открывшемся окне нажмем кнопку Автоматическое подключение...
  3. Установим флаг Фоновые задания и нажмем ОК.

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

Шаг 3. Анализ причины удаления строк и поиск ошибки

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


//+Общепит
// Пропустить группы. Группы в выборке есть при иерархической сортировке.
Если Выборка.КоличествоУчет = 0 И Выборка.СуммаДляЦены = 0 Тогда
    Продолжить;
КонецЕсли;
//-Общепит

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

Варианты исправления проблемы

Для восстановления корректной работы кнопки "Перезаполнить учетные количества и суммы" можно использовать несколько подходов:

  1. Доработка условия в коде: Разделить логику выполнения операций. Проверка Выборка.КоличествоУчет = 0 должна вычисляться только при первоначальном заполнении документа по остаткам (когда происходит полное формирование табличной части), но не при перезаполнении учетных сумм по существующим строкам.
  2. Создание расширения конфигурации: Чтобы не снимать конфигурацию с поддержки, перехватить вызываемую серверную процедуру в расширении с помощью аннотации &Вместо или &ИзменениеИОбработка и реализовать корректное обновление колонок только для текущих строк табличной части Объект.Товары.
← На главную