Почему в отчете СКД не работает отбор по периоду при использовании виртуальных таблиц?

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

При разработке отчетов на Системе компоновки данных (СКД) программисты часто сталкиваются с ситуацией, когда запрос, идеально работающий в консоли запросов, начинает вести себя странно в составе отчета. Типичный симптом: пользователь устанавливает период в настройках, нажимает кнопку "Сформировать", но отчет либо выводит данные за все время, либо поля периода на форме очищаются, а результат игнорирует заданные границы. Особенно часто это проявляется при использовании виртуальных таблиц, таких как СрезПоследних.

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

Разбираем причину: механизмы автоматизации СКД

Рассмотрим ситуацию, когда в запросе соединяются таблица документов и виртуальная таблица РегистрСведений.ЦеныНоменклатуры.СрезПоследних. Основная проблема заключается в том, что 1С СКД — это не просто инструмент выполнения текста запроса, а интеллектуальный генератор. Когда система видит в тексте запроса виртуальную таблицу, она автоматически добавляет в список параметров скрытый параметр &Период.

Проанализируем, к чему это приводит:

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

Решение 1: Правильная настройка связей параметров

Выясним, как подружить пользовательский ввод и требования виртуальных таблиц. Если мы используем на форме СтандартныйПериод (с выбором "Месяц", "Квартал" и т.д.), нам нужно явно передать границы этого периода в параметры запроса.

Выполним следующие шаги в конструкторе СКД на закладке "Параметры":

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

Решение 2: Использование расширения языка запросов (фигурные скобки)

Проанализируем ситуацию, когда нам нужна максимальная гибкость. Чтобы СКД корректно подставляла параметры в виртуальную таблицу только тогда, когда они заданы пользователем, используем фигурные скобки. Посмотрим на пример правильного синтаксиса соединения:


ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ЦеныНоменклатуры.СрезПоследних({&ДатаОкончания}, ) КАК ЦеныНоменклатурыСрезПоследних
ПО ОтчетПроизводстваЗаСменуПродукция.Номенклатура = ЦеныНоменклатурыСрезПоследних.Номенклатура

Важный момент: Если вы используете автозаполнение в СКД, система сама пытается управлять параметрами. Если вы хотите полного контроля, галочку Автозаполнение в конструкторе запроса можно снять, но тогда вам придется вручную описать все поля выбора и отборов в секциях {ВЫБРАТЬ...}, {ГДЕ...}.

Решение 3: Методика "Временные таблицы" (Монстрик)

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

Разберем алгоритм по шагам:

  1. Первый пакет запроса: Выбираем только необходимые данные из документов (номенклатуру, ссылки, количество) с отбором по периоду и помещаем их во временную таблицу ВТ_ДанныеДокументов.
  2. Второй пакет запроса: Выбираем цены из регистра, ограничивая выборку только той номенклатурой, которая попала в первую временную таблицу. Это значительно ускоряет отчет.
  3. Третий пакет запроса: Соединяем временную таблицу документов с данными о ценах.

Пример структуры такого запроса:


ВЫБРАТЬ
    Продукция.Номенклатура КАК Номенклатура,
    Продукция.Ссылка КАК Документ
ПОМЕСТИТЬ ВТ_Документы
ИЗ
    Документ.ОтчетПроизводстваЗаСмену.Продукция КАК Продукция
ГДЕ
    Продукция.Ссылка.Дата МЕЖДУ &ДатаНачала И &ДатаОкончания;

////////////////////////////////////////////////////////////////////////////////
ВЫБРАТЬ
    ВТ_Документы.Номенклатура,
    Цены.Цена
ИЗ
    ВТ_Документы КАК ВТ_Документы
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ЦеныНоменклатуры.СрезПоследних(&ДатаОкончания, Номенклатура В (ВЫБРАТЬ Номенклатура ИЗ ВТ_Документы)) КАК Цены
ПО ВТ_Документы.Номенклатура = Цены.Номенклатура

Проверка результата и отладка

Если после всех манипуляций отчет все еще ведет себя некорректно, рекомендуем воспользоваться инструментом "Консоль компоновки данных". В отличие от обычной консоли запросов, она позволяет увидеть "итоговый" запрос, который СКД генерирует непосредственно перед отправкой в СУБД.

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

Совет: Всегда проверяйте значения полей на NULL при левом соединении с ценами. Используйте конструкцию ЕСТЬNULL(Цены.Цена, 0), чтобы избежать пустых ячеек в отчете и ошибок при расчетах итогов.

Таким образом, правильная работа с периодом в СКД требует понимания того, как система связывает параметры виртуальных таблиц с пользовательскими настройками. Используя явное описание параметров в выражениях или структуру с временными таблицами, вы добьетесь стабильной и предсказуемой работы ваших отчетов.

← На главную