Почему не работает группировка в динамическом списке 1С и как это исправить

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

При разработке управляемых форм разработчики нередко сталкиваются с ситуацией: в тексте произвольного запроса динамического списка прописана конструкция СГРУППИРОВАТЬ ПО (или ВЫБРАТЬ РАЗЛИЧНЫЕ), синтаксических ошибок нет, однако в результирующей таблице на форме строки не сворачиваются и продолжают дублироваться. Разберем причины такого поведения платформы 1С:Предприятие и рассмотрим практические способы решения задачи.

В чем причина некорректной работы СГРУППИРОВАТЬ ПО

Проанализируем ситуацию на примере запроса к регистру сведений РегистрСведений.КонтактнаяИнформация:


ВЫБРАТЬ
    КонтактнаяИнформация.Объект КАК КонтактноеЛицо,
    КонтактнаяИнформация.Объект.Должность КАК Должность
ИЗ
    РегистрСведений.КонтактнаяИнформация КАК КонтактнаяИнформация
ГДЕ
    ТИПЗНАЧЕНИЯ(КонтактнаяИнформация.Объект) = ТИП(Справочник.КонтактныеЛица)
    И КонтактнаяИнформация.Объект.ОбъектВладелец = &ОбъектВладелец
СГРУППИРОВАТЬ ПО
    КонтактнаяИнформация.Объект,
    КонтактнаяИнформация.Объект.Должность

Выясним причину, почему такой запрос не сворачивает строки на форме. Главный фактор — заполненное свойство «Основная таблица» в настройках динамического списка.

Когда у динамического списка указана основная таблица (в данном примере — таблица регистра сведений), платформа 1С автоматически модифицирует исходный запрос при трансляции в СУБД. Для обеспечения динамического постраничного считывания порций данных, позиционирования курсора и работы стандартных команд платформе требуются уникальные системные идентификаторы. В итоговый SQL-запрос принудительно подмешиваются ключевые поля (для регистра сведений это измерения, период, номер строки, формирующие КлючЗаписи; для справочников и документов — Ссылка).

Наличие уникальных ключевых полей в скрытой выборке делает каждую запись уникальной, полностью нивелируя оператор СГРУППИРОВАТЬ ПО верхнего уровня. В результате пользователь видит на форме несгруппированные строки.

Кроме того, важно различать два принципиально разных понятия:

  1. Агрегация строк в СУБД: сворачивание повторяющихся записей на уровне выборки данных с помощью предложений СГРУППИРОВАТЬ ПО или ВЫБРАТЬ РАЗЛИЧНЫЕ.
  2. Визуальная иерархическая группировка СКД: отображение данных в виде дерева с раскрывающимися ветками/папками, которое настраивается в структуре настроек компоновщика динамического списка.

Способ 1. Изоляция группировки во вложенном запросе

Если нам требуется именно свернуть дублирующиеся строки на уровне СУБД и получить плоский список уникальных комбинаций, поместим агрегирующий запрос во вложенную таблицу.

Посмотрим на пример реализации:


ВЫБРАТЬ
    Вложенный.КонтактноеЛицо КАК КонтактноеЛицо,
    Вложенный.Должность КАК Должность
ИЗ
    (ВЫБРАТЬ
        КонтактнаяИнформация.Объект КАК КонтактноеЛицо,
        КонтактнаяИнформация.Объект.Должность КАК Должность
    ИЗ
        РегистрСведений.КонтактнаяИнформация КАК КонтактнаяИнформация
    ГДЕ
        ТИПЗНАЧЕНИЯ(КонтактнаяИнформация.Объект) = ТИП(Справочник.КонтактныеЛица)
        И КонтактнаяИнформация.Объект.ОбъектВладелец = &ОбъектВладелец
    СГРУППИРОВАТЬ ПО
        КонтактнаяИнформация.Объект,
        КонтактнаяИнформация.Объект.Должность) КАК Вложенный

В этом случае платформа надстраивает свои служебные конструкции только над внешним запросом, не разрушая оператор СГРУППИРОВАТЬ ПО внутри подзапроса. Все строки будут корректно свернуты.

Способ 2. Очистка свойства «Основная таблица»

Разберем еще один вариант: если динамическому списку не требуются механизмы стандартной контекстной обработки основной таблицы (например, стандартное открытие формы объекта при двойном клике или автоматическая работа команды добавления), очистим поле «Основная таблица» в палитре свойств динамического списка.

Когда основная таблица не задана, платформа выполняет пользовательский запрос в исходном виде без принудительного добавления ключевых полей, и предложение СГРУППИРОВАТЬ ПО отрабатывает штатно.

Способ 3. Настройка визуального дерева через структуру СКД

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

Разберем по шагам, как это сделать:

  1. В свойствах динамического списка откроем окно «Настройка списка».
  2. Перейдем на закладку «Группировка».
  3. Добавим требуемое поле группировки (например, поле Должность или КонтактноеЛицо) и укажем тип группировки (элементы, группы и элементы).

Также группировку можно задать программно при инициализации формы. Посмотрим на пример кода в событии ПриСозданииНаСервере:


&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
    // Очищаем текущую структуру группировок
    Список.КомпоновщикНастроек.Настройки.Структура.Очистить();
    
    // Создаем новую группировку компоновки данных
    Группа = Список.КомпоновщикНастроек.Настройки.Структура.Добавить(Тип("ГруппировкаКомпоновкиДанных"));
    Группа.Использование = Истина;
    
    // Задаем поле группировки
    ПолеГруппы = Группа.ПоляГруппировки.Элементы.Добавить(Тип("ПолеГруппировкиКомпоновкиДанных"));
    ПолеГруппы.Поле = Новый ПолеКомпоновкиДанных("КонтактноеЛицо");
    ПолеГруппы.Использование = Истина;
    ПолеГруппы.ТипГруппировки = ТипГруппировкиКомпоновкиДанных.Элементы;
КонецПроцедуры

Ограничения платформы и рекомендации по оптимизации

Рассмотрим важные нюансы, которые необходимо учитывать при работе с группировками в динамических списках:

  1. Режим динамического считывания: При очистке свойства «Основная таблица» или использовании сложных вложенных подзапросов платформа отключает постраничное считывание порций данных. Выборка начинает считываться пачками (от 1000 записей), что на больших таблицах может вызывать заметные задержки при открытии формы и увеличенное потребление оперативной памяти.
  2. Отсутствие агрегатных итогов: В отличие от отчетов СКД, динамический список в режиме визуальной группировки не рассчитывает промежуточные агрегатные итоги (суммы, средние) по сформированным веткам дерева.
  3. Индексация полей: Для быстрого раскрытия веток иерархической группировки критически важно наличие индекса в базе данных по группируемым полям.
  4. Оптимизация источника данных: Если требуется отображать список контактных лиц конкретного владельца, эффективнее строить динамический список от таблицы Справочник.КонтактныеЛица (с указанием ее в качестве основной таблицы и отбором по реквизиту ОбъектВладелец), а необходимые поля регистра сведений присоединять через левое соединение. Это исключает тяжелые конструкции с ТИПЗНАЧЕНИЯ по составным типам регистра сведений.
← На главную