Разработка и Конфигурация · 12 мин
Как в 1С передать таблицу в динамический список
Как в 1С передать таблицу значений в динамический список: произвольный запрос, временная таблица, основная таблица, настройка через СКД. Примеры кода и типичные ошибки.
Динамический список в управляемых формах 1С по умолчанию строится на запросе к таблицам информационной базы. Но часто данные уже собраны программно — в таблице значений, полученной из обмена, расчёта или сложной выборки, — и возникает задача показать их именно через динамический список с его сортировкой, отборами и поиском. Прямого свойства «ИсточникДанных» у динамического списка нет, поэтому таблицу передают косвенно: через временную таблицу в произвольном запросе.
Механизм основан на возможностях конструктора запросов: таблица значений помещается во временную таблицу оператором ПОМЕСТИТЬ, а динамический список читает её как обычный источник. Такой подход работает и в ручной настройке запроса динамического списка, и при программной установке текста запроса через свойство ПроизвольныйЗапрос.
Ниже разобраны рабочий способ передачи таблицы, ограничения платформы, вариант с внешним набором данных через СКД и типичные ошибки, из-за которых список остаётся пустым или падает с ошибкой запроса.
Почему таблицу нельзя передать напрямую
Динамический список — это не контейнер данных, а описание запроса, который платформа выполняет сама при прокрутке, отборе или сортировке. Он не хранит строки в памяти формы, а каждый раз обращается к источнику. Поэтому свойства вроде «Загрузить(ТаблицаЗначений)» у динамического списка не существует в принципе.
Единственный «вход» для внешних данных — параметры запроса. А запрос 1С умеет принимать таблицу значений как параметр и разворачивать её во временную таблицу конструкцией ВЫБРАТЬ ... ПОМЕСТИТЬ ИмяВТ ИЗ &Таблица КАК Т. Именно этой возможностью и пользуются.
Альтернатива — отказаться от динамического списка и показать таблицу в элементе формы «ТаблицаФормы», привязанном к реквизиту типа «ТаблицаЗначений». Это проще, но теряются встроенные отборы, поиск по строке и динамическое считывание.
Базовый способ: временная таблица в произвольном запросе
Последовательность одинакова для формы списка, формы выбора и динамического списка на произвольной форме. Сначала в свойствах динамического списка включается флаг «Произвольный запрос», затем текст запроса оформляется как пакетный: первый запрос создаёт временную таблицу из параметра, второй выбирает из неё данные.
Пример текста запроса:
ВЫБРАТЬ
Т.Номенклатура КАК Номенклатура,
Т.Количество КАК Количество,
Т.Сумма КАК Сумма
ПОМЕСТИТЬ ВТ_Данные
ИЗ
&ТаблицаДанных КАК Т
;
ВЫБРАТЬ
ВТ.Номенклатура КАК Номенклатура,
ВТ.Количество КАК Количество,
ВТ.Сумма КАК Сумма
ИЗ
ВТ_Данные КАК ВТ
Далее в модуле формы, например в обработчике ПриСозданииНаСервере, таблица передаётся как параметр списка:
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
ТаблицаДанных = ПолучитьТаблицуДанных(); // своя функция формирования
Список.Параметры.УстановитьЗначениеПараметра("ТаблицаДанных", ТаблицаДанных);
КонецПроцедуры
- 1Откройте свойства динамического списка и установите флаг «Произвольный запрос»
- 2Напишите пакетный запрос: ПОМЕСТИТЬ параметр-таблицу во временную таблицу, затем выберите из неё поля
- 3Укажите ключевое поле списка (например, ссылку или уникальный идентификатор строки)
- 4В ПриСозданииНаСервере сформируйте таблицу значений с колонками, совпадающими по именам с полями первого запроса
- 5Передайте таблицу через Список.Параметры.УстановитьЗначениеПараметра
- 6Откройте форму и проверьте, что строки отображаются, а отбор и сортировка работают
Имена колонок таблицы значений должны совпадать с именами полей, указанными в первом запросе пакета, а типы колонок — быть явно заданными через ТаблицаЗначений.Колонки.Добавить("Сумма", Новый ОписаниеТипов("Число")). Нетипизированные колонки частая причина ошибки «Неверные параметры в операции сравнения» или пустого результата при отборах.
Настройка ключевого поля и основной таблицы
Динамический список требует уникальности строк. Если флаг «Основная таблица» не установлен (а для произвольного запроса с временной таблицей его обычно снимают), платформа сама пытается определить ключ записи. При дублях значений в поле, которое список считает ключевым, строки начинают «склеиваться» или дублироваться при прокрутке.
Надёжное решение — добавить в таблицу служебную колонку с уникальным значением (например, строковое представление нового УникальныйИдентификатор) и указать её в свойстве «Ключевое поле» динамического списка:
ТаблицаДанных.Колонки.Добавить("КлючСтроки", Новый ОписаниеТипов("Строка", , , , Новый КвалификаторыСтроки(36)));
Для Каждого Строка Из ТаблицаДанных Цикл
Строка.КлючСтроки = Строка(Новый УникальныйИдентификатор);
КонецЦикла;
Если строки списка должны открываться как объекты (например, элементы справочника), ключевым полем делают ссылку, а основную таблицу оставляют установленной — тогда платформа связывает временную таблицу с таблицей справочника соединением. Но это работает только когда в данных действительно есть ссылки на существующие объекты.
Программная установка запроса и обновление данных
Текст запроса можно менять из кода, что удобно, когда структура данных известна только в момент выполнения. Для этого у динамического списка программно устанавливаются свойства ПроизвольныйЗапрос, ТекстЗапроса и при необходимости ОсновнаяТаблица:
Список.ПроизвольныйЗапрос = Истина;
Список.ТекстЗапроса =
"ВЫБРАТЬ Т.Ссылка КАК Ссылка, Т.Показатель КАК Показатель
|ПОМЕСТИТЬ ВТ ИЗ &Таблица КАК Т
|;
|ВЫБРАТЬ ВТ.Ссылка КАК Ссылка, ВТ.Показатель КАК Показатель ИЗ ВТ КАК ВТ";
Список.Параметры.УстановитьЗначениеПараметра("Таблица", ТаблицаДанных);
При обновлении данных достаточно повторно установить параметр новой таблицей — список перечитает данные сам. Принудительно обновить отображение можно через Элементы.Список.Обновить(). Если параметр устанавливается в ПриСозданииНаСервере, дополнительного обновления обычно не требуется.
Учитывайте, что текст запроса, заданный программно, перекрывает настройку из конфигуратора, а пользовательские настройки отбора могут ссылаться на поля, которых в новом запросе нет, — тогда отбор просто перестанет применяться или вызовет ошибку. Поля, доступные для отбора, стоит фиксировать в настройках списка.
Альтернатива: внешний набор данных через СКД
Если требуется не просто список, а гибкая настройка группировок и итогов, вместо произвольного запроса используют схему компоновки данных с источником «Объект». В этом случае динамический список переводится в режим основной таблицы СКД, а таблица значений передаётся как внешний набор данных при компоновке.
На практике этот путь чаще применяют для отчётов, а не для экранных списков: настройка заметно сложнее, а выигрыш для простого табличного показа невелик. Для задачи «показать таблицу с отбором и сортировкой» пакетный запрос с временной таблицей проще и предсказуемее.
Сравнение вариантов
Подходит для большинства экранных списков: сохраняются отборы, сортировка, поиск. Ограничение — накладные расходы на больших объёмах и обязательная типизация колонок.
Проще всего в реализации, данные полностью под контролем кода. Нет встроенного динамического считывания, отборы и поиск придётся делать вручную.
Подходит для больших объёмов и периодически обновляемых данных: список читает обычную таблицу БД. Требует записи данных и продумывания очистки устаревших строк.
Даёт группировки, итоги и гибкие настройки. Избыточен для простого списка, сложнее в отладке и сопровождении.
Типичные ошибки и как их диагностировать
Самая частая ситуация — пустой список без сообщений об ошибке. Причины почти всегда одни и те же: параметр не установлен до первого обращения списка к данным, имена колонок таблицы не совпадают с полями запроса или таблица значений вообще не заполнена из-за ошибки в функции её формирования.
Вторая группа проблем — ошибки запроса вида «Поле не найдено» или «Неверные параметры». Они возникают, когда колонка добавлена без типа, имя поля отличается регистром или опечаткой, либо в запросе используется поле, которого нет во временной таблице. Проверяется это выгрузкой таблицы в отладчике: ТаблицаДанных.Колонки должны точно соответствовать списку полей первого запроса пакета.
Третья группа — «плавающие» строки: при прокрутке одна и та же строка появляется несколько раз или исчезает. Это признак неуникального ключевого поля. Лечится добавлением служебной колонки с уникальным идентификатором и указанием её как ключевой.
Проверка результата
Минимальная проверка выполняется прямо в пользовательском режиме: форма открывается, список показывает ожидаемое количество строк, сортировка по числовой и строковой колонкам работает в обе стороны, отбор по ссылочному полю возвращает корректное подмножество.
Дополнительно стоит проверить повторное открытие формы и обновление по кнопке F5 — данные не должны задваиваться. Если список используется для выбора, проверяется, что двойной щелчок по строке возвращает правильное значение, а не пустую ссылку.
Как проверить результат
Все строки таблицы видны, количество совпадает с исходной таблицей
Список пуст или строк меньше, чем в источнике
Сортировка меняет порядок, отбор сужает список корректно
Ошибка запроса или отбор не влияет на результат
Каждая строка встречается один раз
Строки повторяются или исчезают — проблема с ключевым полем
Форма открывается без заметной паузы
Задержка в секунды — таблица слишком велика для параметра
FAQ
Можно ли передать в динамический список таблицу значений без запроса?
Нет. Динамический список всегда работает через запрос. Таблица значений попадает в него только как параметр, который запрос помещает во временную таблицу. Если запрос не нужен в принципе, используйте реквизит формы типа «ТаблицаЗначений» и элемент «ТаблицаФормы».
Почему список пустой, хотя таблица заполнена?
Чаще всего параметр установлен с опечаткой в имени, позже первого обращения списка к данным, или имена колонок таблицы не совпадают с полями запроса. Проверьте в отладчике состав колонок и момент вызова УстановитьЗначениеПараметра — он должен быть в ПриСозданииНаСервере до отображения формы.
Обязательно ли типизировать колонки таблицы значений?
Да. Колонка без описания типов получает составной тип, и отборы или сравнения по ней в запросе могут завершиться ошибкой несовместимости типов. Всегда передавайте второй параметр в Колонки.Добавить с явным ОписаниеТипов.
Как обновить данные списка после изменения таблицы?
Повторно вызовите Список.Параметры.УстановитьЗначениеПараметра с новой таблицей и при необходимости Элементы.Список.Обновить(). Отдельной команды «перезагрузить таблицу» у динамического списка нет — перечитывание инициируется сменой параметра.
Есть ли ограничение на размер передаваемой таблицы?
Жёсткого ограничения платформа не задаёт, но параметр-таблица разворачивается во временную таблицу при каждом обращении списка к данным. На крупных объёмах это даёт заметную нагрузку. Практический порог — десятки тысяч строк; дальше надёжнее записывать данные в регистр сведений и строить список по нему.
Работает ли этот способ в динамическом списке формы выбора?
Да, механизм идентичен: произвольный запрос с временной таблицей, параметр через Параметры списка, ключевое поле со ссылкой или уникальным идентификатором. Дополнительно проверьте, что при выборе строки возвращается ожидаемое значение.
Что важно запомнить
Таблица передаётся в динамический список только через параметр произвольного запроса с помещением во временную таблицу. Обязательны: типизированные колонки, уникальное ключевое поле и установка параметра до первого обращения списка к данным. Для больших объёмов вместо параметра используйте промежуточный регистр сведений.