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

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

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

Вторая популярная проблема, которую мы проанализируем — это ограничение количества выводимых записей в отчете, когда использование конструкции ВЫБРАТЬ ПЕРВЫЕ &МаксимумЗаписей напрямую в тексте запроса недоступно.

Разберем проблему появления лишних полей в колонках СКД

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

  1. Работа с элементом "Автополе". Самый быстрый способ убрать лишние реквизиты — перейти в Конфигуратор и открыть настройки СКД. На вкладке "Настройки" выберите ту группировку, где не нужно выводить все подряд поля. Перейдите в "Выбранные поля" этой группировки, найдите Автополе, разверните его и снимите флажки с ненужных полей, либо полностью удалите Автополе и добавьте только те реквизиты, которые действительно нужны.
  2. Отключение автозаполнения запроса. По умолчанию в наборе данных запроса СКД включен флаг "Автозаполнение". Платформа автоматически подтягивает в настройки все реквизиты выбранных таблиц. Самый надежный и жесткий способ контролировать вывод — снять галку "Автозаполнение" в конструкторе запроса СКД. После этого на специальной вкладке "Компоновка данных" потребуется вручную прописать необходимые поля для выборки и группировок.
  3. Ограничение доступности полей. Чтобы пользователи не могли случайно вытянуть служебные или ненужные поля, на вкладке "Наборы данных" используйте специальные флажки: Ограничение поля, Ограничение условий, Ограничение реквизитов. Установив их, вы физически скроете эти поля из списка доступных для конечного пользователя.

Как ограничить количество выводимых записей в СКД?

Разработчики часто хотят дать пользователю возможность задать параметр (например, "Максимум записей" = 100), чтобы не перегружать отчет. Платформа 1С не позволяет просто написать в тексте запроса СКД ВЫБРАТЬ ПЕРВЫЕ &Параметр. Посмотрим на альтернативные варианты решения этой задачи.

Вариант 1. Программная модификация через объект СхемаЗапроса

Это самый производительный подход, так как ограничение отработает на уровне СУБД. Начиная с версий платформы 8.3, мы можем перехватить запрос перед выполнением в обработчике ПриКомпоновкеРезультата и изменить его структуру программно.

Проанализируем алгоритм:

  1. Получаем из пользовательских настроек (или параметров) желаемое количество записей.
  2. Помещаем текст запроса набора данных в объект СхемаЗапроса.
  3. Модифицируем свойство КоличествоПолучаемыхЗаписей у нужного оператора в пакете запросов.
  4. Возвращаем измененный текст обратно в СКД.

Пример программного кода в модуле объекта отчета:


Процедура ПриКомпоновкеРезультата(ДокументРезультат, ДанныеРасшифровки, СтандартнаяОбработка)
    
    СтандартнаяОбработка = Ложь;
    
    // Получаем значение параметра из настроек
    МаксимумЗаписей = 100; // Здесь должен быть код получения значения параметра "МаксимумЗаписей"
    
    Схема = СхемаКомпоновкиДанных;
    НаборДанных = Схема.НаборыДанных.Найти("НаборДанных1");
    
    Если НаборДанных <> Неопределено Тогда
        
        СхемаЗапроса = Новый СхемаЗапроса;
        СхемаЗапроса.УстановитьТекстЗапроса(НаборДанных.Запрос);
        
        // Устанавливаем лимит записей для первого пакета запроса
        СхемаЗапроса.ПакетЗапросов[0].Операторы[0].КоличествоПолучаемыхЗаписей = МаксимумЗаписей;
        
        НаборДанных.Запрос = СхемаЗапроса.ПолучитьТекстЗапроса();
        
    КонецЕсли;
    
    // Выполняем стандартную компоновку с уже измененной схемой
    КомпоновщикМакета = Новый КомпоновщикМакетаКомпоновкиДанных;
    МакетКомпоновки = КомпоновщикМакета.Выполнить(Схема, КомпоновщикНастроек.ПолучитьНастройки(), ДанныеРасшифровки);
    
    ПроцессорКомпоновки = Новый ПроцессорКомпоновкиДанных;
    ПроцессорКомпоновки.Инициализировать(МакетКомпоновки, , ДанныеРасшифровки, Истина);
    
    ПроцессорВывода = Новый ПроцессорВыводаРезультатаКомпоновкиДанныхВТабличныйДокумент;
    ПроцессорВывода.УстановитьДокумент(ДокументРезультат);
    ПроцессорВывода.Вывести(ПроцессорКомпоновки);

КонецПроцедуры

Вариант 2. Программная установка количества записей в группировках

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

Вариант 3. Нумерация строк и отбор в СКД

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

Создав вычисляемое поле, например НомерСтроки, мы просто добавляем в настройки отчета стандартный отбор вида:

НомерСтроки Меньше или равно &МаксимальноеКоличество

В данном случае запрос к базе данных вернет все строки, но СКД отсечет лишние на этапе компоновки результата, до вывода пользователю. Этот вариант прост в реализации, но менее оптимален с точки зрения производительности при больших объемах данных.

← На главную