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

Программист IT и автоматизация бизнеса
← На главную

При работе со справочниками и документами в управляемом интерфейсе 1С разработчики нередко сталкиваются с проблемой: при попытке прокрутить динамический список вверх или вниз интерфейс «замирает» на несколько секунд. Проблема становится особенно заметной при использовании файловых баз, активных группировок и наложении программных отборов.

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

Причины падения производительности динамического списка

Проанализируем основные факторы, вызывающие зависания при навигации по строкам:

  1. Использование группировок в динамическом списке. Механизм динамического списка оптимизирован для линейных (плоских) выборок с постраничной подгрузкой данных. При включении группировок платформа вынуждена для каждой отображаемой порции рассчитывать количество строк, иерархические связи и итоги, выполняя множество тяжелых агрегатных запросов к СУБД.
  2. Отсутствие индексов по полям отбора и сортировки. Если в списке наложен отбор (например, по менеджеру или подразделению), но соответствующий реквизит не проиндексирован в конфигураторе, движок базы данных выполняет полное сканирование таблицы (Full Scan) при каждом сдвиге курсора или бегунка.
  3. Отключение динамического считывания данных. Снятие флага ДинамическоеСчитываниеДанных приводит к тому, что платформа пытается загрузить в память клиентского приложения всю выборку целиком. При наличии нескольких тысяч записей это вызывает резкий рост потребления памяти и freeze-эффект.
  4. Тяжелый код в событиях формы. Использование процедур ПриАктивизацииСтроки или ПриПолученииДанныхНаСервере с контекстными серверными вызовами заставляет клиент отправлять запросы на сервер при каждом перемещении фокуса.
  5. Особенности файловой СУБД. В файловом режиме блокировка накладывается на уровне таблиц целиком, что при параллельной работе пользователей и фоновых заданий усиливает задержки отклика.

Шаг 1. Индексация реквизитов отбора, сортировки и группировки

Если для динамического списка задаются условия отбора или сортировки, обязательно проверяем индексы полей в конфигураторе.

Рассмотрим порядок настройки:

  1. Откроем дерево метаданных конфигурации и найдем целевой объект (например, справочник Контрагенты).
  2. Перейдем в свойства реквизита, по которому накладывается отбор (например, Менеджер).
  3. Установим свойство Индексировать в значение Индексировать или Индексировать с доп. упорядочиванием (если по этому же полю выполняется регулярная сортировка).
  4. Аналогичным образом проверим поля, используемые в пользовательских группировках.

Шаг 2. Корректная установка программных отборов

Часто в процедуре ПриСозданииНаСервере отбор по текущему пользователю или подразделению накладывается через прямое добавление элементов в коллекцию Список.Отбор.Элементы. Рассмотрим пример такого кода:


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

Проанализируем важные правила работы с программными отборами:

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

Шаг 3. Оптимизация группировок и структуры формы

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

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

Шаг 4. Диагностика запросов через Технологический журнал

Чтобы точно определить, какой именно SQL-запрос генерирует платформа при прокрутке списка, настроим сбор технологического журнала. Это позволит увидеть длительность выполнения запросов и выявить неоптимальные конструкции.

Для регистрации событий СУБД и контекста исполнения создадим файл logcfg.xml в каталоге настроек платформы (bin/conf):


<config xmlns="v8.1c.ru/v8/tech-log">
    <log location="C:\LOGS\1C_Queries" history="24">
        <event>
            <eq property="name" value="DBMSSQL"/>
            <gt property="duration" value="100000"/>
        </event>
        <event>
            <eq property="name" value="DBV8DBEngine"/>
            <gt property="duration" value="100000"/>
        </event>
        <property name="all"/>
    </log>
</config>

Событие DBV8DBEngine собирает информацию о запросах к файловой базе данных, а DBMSSQL — к Microsoft SQL Server. Параметр duration задает порог длительности в микросекундах (в примере — от 100 мс).

Итоги

Для восстановления высокой скорости работы динамического списка в 1С необходимо соблюдать комплекс мер: включить флаг динамического считывания, проиндексировать реквизиты, участвующие в отборах и сортировках, исключить избыточные группировки в форме и очистить обработчик ПриАктивизацииСтроки от синхронных серверных вызовов.

← На главную