Почему динамический список в расширении не видит параметры запроса и как это исправить?

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

При разработке в среде 1С:Предприятие 8.3 программисты часто сталкиваются с ситуацией, когда динамический список в расширении ведет себя иначе, чем в основной конфигурации. Одна из самых неприятных проблем — когда код Список.Параметры.Количество() возвращает 0, хотя в тексте запроса явно указаны параметры через символ &. Рассмотрим подробнее, почему это происходит и как заставить динамический список работать корректно.

Проанализируем причину: почему коллекция параметров пуста?

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

В контексте расширений эта проблема обостряется. Запрос, который успешно работает в консоли запросов или в основной конфигурации, может "сломаться" в расширении по следующим причинам:

  1. Неполное заимствование метаданных. Если в запросе динамического списка используются таблицы или поля, которые не добавлены в расширение, запрос считается невалидным.
  2. Обращение к полям составного типа. Это самая частая причина. В расширениях платформа более строго проверяет типы данных. Если поле (например, Значение в регистре сведений НастройкиПользователей) имеет составной тип, прямое обращение через точку к его реквизитам (Значение.ИИН) приведет к ошибке, так как тип поля неопределен.
  3. Кэширование метаданных. Иногда после изменения запроса в расширении платформа продолжает использовать старую схему.

Разберем решение проблемы с составными типами

Посмотрим на пример запроса, который вызывает ошибку:


ГДЕ СправочникНоменклатура.Родитель.Наименование в (
    ВЫБРАТЬ НастройкиПользователей.Значение.ИИН
    ИЗ РегистрСведений.НастройкиПользователей КАК НастройкиПользователей
    ГДЕ НастройкиПользователей.Настройка = &ОснОрг
)

В данном случае поле Значение является составным. Чтобы динамический список в расширении "увидел" параметры &ОснОрг и &Пользователь, нам необходимо явно указать платформе, к какому типу данных мы обращаемся. Выясним, как это сделать правильно с помощью оператора ВЫРАЗИТЬ.

Изменим запрос следующим образом:


ГДЕ СправочникНоменклатура.Родитель.Наименование в (
    ВЫБРАТЬ ВЫРАЗИТЬ(НастройкиПользователей.Значение КАК Справочник.Организации).ИдентификационныйНомер
    ИЗ РегистрСведений.НастройкиПользователей КАК НастройкиПользователей
    ГДЕ НастройкиПользователей.Настройка = &ОснОрг
    И НастройкиПользователей.Пользователь = &Пользователь
)

Важный момент: Для того чтобы конструкция ВЫРАЗИТЬ(... КАК Справочник.Организации) заработала в расширении, сам справочник Организации и его реквизит ИдентификационныйНомер должны быть обязательно добавлены в это расширение. Если вы используете поле Наименование, убедитесь, что оно также доступно.

Как правильно устанавливать параметры программно

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

Способ 1. Использование встроенных методов динамического списка:


&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
    // Убедимся, что параметр существует в коллекции перед установкой
    Если Список.Параметры.ДоступныеПараметры.Найти("ОснОрг") <> Неопределено Тогда
        Список.Параметры.УстановитьЗначениеПараметра("ОснОрг", ПланыВидовХарактеристик.НастройкиПользователей.ОсновнаяОрганизация);
    КонецЕсли;
    
    Если Список.Параметры.ДоступныеПараметры.Найти("Пользователь") <> Неопределено Тогда
        Список.Параметры.УстановитьЗначениеПараметра("Пользователь", Пользователи.ТекущийПользователь());
    КонецЕсли;
КонецПроцедуры

Способ 2. Использование функций БСП:


&НаСервере
Процедура Расш1_ПриСозданииНаСервереПосле(Отказ, СтандартнаяОбработка)
    ОбщегоНазначенияКлиентСервер.УстановитьПараметрДинамическогоСписка(
        Список, 
        "ОснОрг", 
        ПланыВидовХарактеристик.НастройкиПользователей.ОсновнаяОрганизация
    );
КонецПроцедуры

Преимущество метода БСП в том, что он обычно содержит внутренние проверки и не вызывает исключения, если параметр временно отсутствует (например, если запрос динамически меняется).

Пошаговый алгоритм действий, если параметры "исчезли"

Если вы столкнулись с пустой коллекцией Список.Параметры, выполните следующие шаги:

  1. Проверьте валидность запроса в конфигураторе. Откройте конструктор запроса динамического списка прямо в расширении. Если конструктор выдает ошибку "Поле не найдено", значит, запрос нерабочий. Параметры не появятся, пока вы не исправите ошибку.
  2. Проверьте заимствование объектов. Все таблицы (справочники, регистры), используемые в ВЫБРАТЬ, ГДЕ и СОЕДИНЕНИЕ, должны быть в расширении.
  3. Используйте типизацию для составных полей. Как мы разобрали выше, всегда применяйте ВЫРАЗИТЬ для полей типа ЛюбаяСсылка или составных типов из БСП (поля Значение, Владелец и т.д.).
  4. Очистите кэш. В редких случаях платформа "запоминает" ошибочное состояние. Перезапустите конфигуратор и удалите временные файлы пользователя.
  5. Проверьте программное изменение запроса. Посмотрите, не меняется ли Список.ТекстЗапроса где-то в коде основной конфигурации. Если основная конфигурация полностью заменяет текст запроса в ПриСозданииНаСервере, ваши параметры из метаданных расширения могут быть стерты. В этом случае используйте обработчик После и устанавливайте параметры заново.

Выясним причину ошибки из сообщения №21 в теме: НастройкиПользователей.Значение.ИдентификационныйНомер — Поле не найдено. Это прямое подтверждение того, что платформа не может разрешить путь к данным через составное поле. После исправления этой ошибки через ВЫРАЗИТЬ коллекция параметров Список.Параметры заполнится автоматически, и ваш код заработает.

Таким образом, секрет работы с динамическими списками в расширениях заключается в строгой типизации запросов и контроле состава заимствованных метаданных. Рассмотрим эти правила как обязательный стандарт при разработке расширений для стабильной работы ваших интерфейсов.

← На главную