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

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

При разработке отчетов на Системе Компоновки Данных (СКД) мы часто сталкиваемся с задачей вывода иерархических справочников (например, «Подразделения», «Номенклатура» или «Статьи затрат»). Казалось бы, задача тривиальная: вывести дерево и отсортировать его по коду. Однако на практике разработчики обнаруживают, что папки и элементы прыгают, нарушая логический порядок (например, «06» идет перед «02»), или сортировка работает только на верхнем уровне, а внутри групп — хаос.

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

Суть проблемы: конфликт иерархии и сортировки

Рассмотрим ситуацию, описанную в задаче. У нас есть иерархический справочник, где код элемента является строковым и имеет вид «01», «01.01», «05» и т.д. Мы хотим видеть в отчете стройное дерево, упорядоченное по возрастанию кода.

Часто разработчики совершают следующие действия:

  1. Добавляют сортировку УПОРЯДОЧИТЬ ПО Код в текст запроса.
  2. Добавляют поле Код в настройках сортировки всего отчета.
  3. Используют обработчики представления, чтобы визуально объединить код и наименование.

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

Решение 1: Использование выражения упорядочивания (Самый надежный метод)

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

Давайте выполним настройку по шагам:

  1. Откройте схему компоновки данных.
  2. Перейдите на вкладку Наборы данных (при необходимости здесь можно настроить привилегированный режим выполнения отчета).
  3. Найдите ваше поле Ссылка (или поле, по которому строится иерархия).
  4. В колонке Выражение упорядочивания пропишите: Код (или Ссылка.Код, если поле так называется в запросе).

Что это дает? Теперь, где бы вы ни использовали поле Ссылка в группировках или сортировках, СКД будет знать: «Чтобы сравнить две ссылки и понять, какая из них выше, мне нужно сравнить их коды».

Решение 2: Настройка структуры группировок

Как выяснилось в ходе обсуждения проблемы, структура группировок в настройках отчета играет решающую роль. Ошибкой является попытка настроить общую сортировку для всего отчета, игнорируя настройки конкретной группировки.

Разберем правильный алгоритм настройки на вкладке Настройки:

1. Отключение автоматики
Если у вас добавлена группировка по полю Ссылка с типом «Иерархия», проверьте её параметры. Часто там стоит сортировка «Авто». Рекомендуется зайти в параметры сортировки именно этой группировки (не всего отчета) и явно указать поле Код (или Ссылка.Код).

2. Проверка иерархии
Убедитесь, что вы не пытаетесь сортировать по полю, которого нет в выборке на данном уровне иерархии. Если вы группируете по Подразделение, сортировка должна производиться по атрибутам этого подразделения.

3. Изменение структуры (как помогло автору)
Иногда помогает пересоздание группировки. Попробуйте следующую структуру:

Решение 3: Нюансы запроса и строковых кодов

Хотя СКД часто перестраивает запрос, явное указание сортировки в тексте запроса может помочь, если данные выбираются неоптимально. Однако, здесь есть важный нюанс — тип данных кода.

Если код имеет тип Строка, сортировка будет лексикографической. Это значит:

Убедитесь, что ваши коды имеют фиксированную длину и ведущие нули (например, "001", "002", "010"). Если формат кодов "плавающий" (где-то "1", где-то "01"), корректной сортировки добиться стандартными средствами не получится — придется приводить их к единому формату в запросе.

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


ВЫБРАТЬ
    Подразделения.Ссылка КАК Ссылка,
    Подразделения.Код КАК Код,
    Подразделения.Наименование КАК Наименование
ИЗ
    Справочник.Подразделения КАК Подразделения

УПОРЯДОЧИТЬ ПО
    Код

Важно: Упорядочивание в запросе может игнорироваться, если в настройках СКД задана другая сортировка. Приоритет всегда у настроек компоновки.

Особенности работы с представлением

В рассматриваемой задаче автор использовал переопределение представления через событие менеджера:


Процедура ОбработкаПолученияПредставления(Данные, Представление, СтандартнаяОбработка)
    СтандартнаяОбработка = Ложь;
    Представление = СтрЗаменить(Данные.Ссылка.Код," ","") + " " + Данные.Наименование; 
КонецПроцедуры

Нужно понимать, что это влияет только на то, как пользователь видит данные. Для СКД поле по-прежнему остается ссылкой. Не пытайтесь сортировать по полю «Представление» — это ресурсоемкая операция, так как представление формируется динамически уже после выборки данных. Всегда сортируйте по реквизитам базы данных (Код, Наименование, РеквизитУпорядочивания).

Резюме

Для корректной сортировки иерархии в СКД:

  1. Задайте Выражение упорядочивания для поля ссылки на вкладке «Наборы данных». Это самый действенный метод.
  2. Настраивайте сортировку непосредственно в свойствах группировки, а не только на уровне всего отчета.
  3. Следите за форматом строковых кодов (используйте ведущие нули).
  4. Не полагайтесь на сортировку по динамически формируемому представлению.
← На главную