Как вывести счета по иерархии с родительскими группами в отчете 1С 8.3

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

При разработке бухгалтерских отчетов в 1С (например, отчетов по отклонениям остатков или оборотно-сальдовых ведомостей) часто возникает задача: пользователь выбирает в фильтре конкретные рабочие субсчета (например, 231, 281), а в результирующем отчете требуется отобразить не только выбранные счета, но и их родительские группы (счет 20) с корректным расчетом промежуточных итогов.

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

Почему родительские счета не выводятся автоматически

Проанализируем специфику работы с планами счетов и регистрами бухгалтерии в платформе 1С:

  1. Отсутствие проводок по счетам-родителям. В типовых конфигурациях проводки формируются исключительно по счетам нижнего уровня (субсчетам), у которых признак ЗапретитьИспользоватьВПроводках равен Ложь. Виртуальная таблица РегистрБухгалтерии.Хозрасчетный.ОстаткиИОбороты физически не содержит записей по счетам-группам. Если передать родительский счет в условие Счет В (&Счет), запрос не вернет по нему данных.
  2. Ограничения временных таблиц в запросах. Конструкция ИТОГИ ПО ... ИЕРАРХИЯ не может применяться в запросах, использующих оператор ПОМЕСТИТЬ.
  3. Особенности выгрузки во внешний набор данных СКД. Когда результат запроса передается в компоновку через ТаблицаЗначений, поля родительских группировок будут пустыми до тех пор, пока они не будут явно настроены на вкладке Ресурсы схемы компоновки данных.

Способ 1. Использование встроенной иерархии в Системе компоновки данных (рекомендуемый)

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

Разберем по шагам настройку схемы компоновки данных (СКД):

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

При выводе отчета процессор компоновки данных автоматически определит родителей для всех выгруженных счетов, создаст вышестоящие узлы и рассчитает по ним суммы числовых ресурсов.

Способ 2. Использование секции ИТОГИ ПО ИЕРАРХИЯ в запросе (ручной вывод)

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

Посмотрим на пример построения секции итогов в финальной части запроса:


ВЫБРАТЬ
    ВТ_Отклонение.Организация КАК Организация,
    ВТ_Отклонение.Счет КАК Счет,
    ВТ_Отклонение.СуммаКонечныйОстатокДт - ВТ_Отклонение1.СуммаКонечныйОстатокДт КАК ОтклонениеДт,
    ВТ_Отклонение.СуммаКонечныйОстатокКт - ВТ_Отклонение1.СуммаКонечныйОстатокКт КАК ОтклонениеКт
ИЗ
    ВТ_Отклонение КАК ВТ_Отклонение
    ВНУТРЕННЕЕ СОЕДИНЕНИЕ ВТ_Отклонение КАК ВТ_Отклонение1
        ПО ВТ_Отклонение.Счет = ВТ_Отклонение1.Счет
ИТОГИ
    СУММА(ОтклонениеДт),
    СУММА(ОтклонениеКт)
ПО
    Счет ИЕРАРХИЯ

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


РезультатЗапроса = Запрос.Выполнить();
ВыборкаВерхнийУровень = РезультатЗапроса.Выбрать(ОбходРезультатаЗапроса.ПоГруппировкамСИерархией);

Пока ВыборкаВерхнийУровень.Следующий() Цикл
    // Вывод родительского счета или детальной записи
    ТабДок.Вывести(ОбластьСчет);
    
    ВыборкаДетали = ВыборкаВерхнийУровень.Выбрать();
    Пока ВыборкаДетали.Следующий() Цикл
        // Вывод подчиненных субсчетов
        ТабДок.Вывести(ОбластьСубсчет);
    КонецЦикла;
КонецЦикла;

Способ 3. Программное добавление родителей в массив счетов

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


СпСчетовСРодителями = Новый Массив;

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

Важно: если добавить родительские счета в условие Счет В (&Счет), остатки из регистра по ним все равно не вернутся, так как проводки привязаны к субсчетам. Поэтому расчет суммовых показателей по добавленным родительским счетам необходимо производить в ресурсах СКД либо программно при обходе таблицы значений.

← На главную