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