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