К статье
Практический материал

Отчеты и Аналитика · 11 мин

СКД 1С: как выразить поле как документ

Как использовать ВЫРАЗИТЬ в запросе СКД 1С для приведения составного типа к конкретному документу: синтаксис, обращение к реквизитам, ошибки и альтернативы.

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

Конструкция выглядит так: ВЫРАЗИТЬ(Регистратор КАК Документ.РеализацияТоваровУслуг). После приведения платформа «понимает», что значение — это ссылка на конкретный вид документа, и разрешает обращаться к его реквизитам через точку. Для всех строк, где регистратор имеет другой тип, результат выражения будет NULL.

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

Где именно применяется ВЫРАЗИТЬ и зачем оно нужно

Оператор ВЫРАЗИТЬ работает на уровне языка запросов, поэтому используется в тексте запроса набора данных СКД (закладка «Наборы данных» → поле «Запрос»). Сам по себе конструктор СКД не имеет отдельной настройки «выразить как документ» — всё делается в запросе.

Типовые ситуации, когда без приведения типа не обойтись:

  • обращение к реквизиту регистратора: Регистратор.Контрагент не сработает, пока регистратор не приведён к конкретному документу;
  • соединение таблицы регистра с таблицей документа по ссылке составного типа — без ВЫРАЗИТЬ соединение технически возможно, но обращение к реквизитам документа всё равно потребует приведения;
  • отбор по реквизиту документа: например, показать движения только тех реализаций, где склад равен заданному;
  • сравнение поля составного типа с параметром-ссылкой конкретного типа.

Синтаксис приведения к документу

Базовая форма в запросе набора данных:

ВЫБРАТЬ

Продажи.Регистратор КАК Регистратор,

ВЫРАЗИТЬ(Продажи.Регистратор КАК Документ.РеализацияТоваровУслуг).Контрагент КАК Контрагент,

Продажи.КоличествоОборот КАК Количество

ИЗ

РегистрНакопления.Продажи.Обороты(, , Регистратор, ) КАК Продажи

Здесь поле «Регистратор» имеет составной тип (любой документ, который может делать движения по регистру). Выражение ВЫРАЗИТЬ(... КАК Документ.РеализацияТоваровУслуг) приводит его к конкретному виду, и дальше через точку доступен реквизит «Контрагент». Для строк, где регистратор — другой документ (например, «Возврат товаров от покупателя»), поле «Контрагент» будет NULL.

Обратите внимание: имя документа указывается без кавычек, как оно задано в метаданных конфигурации. Ошибка в имени приведёт к ошибке проверки запроса ещё в конструкторе.

bsl
ВЫРАЗИТЬ(Продажи.Регистратор КАК Документ.РеализацияТоваровУслуг).Контрагент КАК Контрагент

Сценарий: несколько видов документов в одном поле

Объединение через ВЫБОР

Если регистратором может быть несколько видов документов и нужно вытащить «Контрагента» из каждого, применяют конструкцию ВЫБОР с несколькими приведениями:

ВЫБОР

КОГДА Продажи.Регистратор ССЫЛКА Документ.РеализацияТоваровУслуг

ТОГДА ВЫРАЗИТЬ(Продажи.Регистратор КАК Документ.РеализацияТоваровУслуг).Контрагент

КОГДА Продажи.Регистратор ССЫЛКА Документ.ВозвратТоваровОтПокупателя

ТОГДА ВЫРАЗИТЬ(Продажи.Регистратор КАК Документ.ВозвратТоваровОтПокупателя).Контрагент

ИНАЧЕ NULL

КОНЕЦ КАК Контрагент

Проверка ССЫЛКА Документ.Имя отсекает ненужные типы до обращения к реквизиту. Это и надёжнее, и читабельнее: сразу видно, какие документы обрабатываются.

Соединение с таблицей документа

Альтернатива — левое соединение с таблицей документа по ссылке:

ЛЕВОЕ СОЕДИНЕНИЕ Документ.РеализацияТоваровУслуг КАК Реализация

ПО Продажи.Регистратор = Реализация.Ссылка

Такой вариант предпочтительнее, когда из документа нужно несколько реквизитов: не придётся повторять ВЫРАЗИТЬ для каждого поля. Соединение само по себе отсекает чужие типы — строки с другими документами просто получат NULL в полях таблицы «Реализация».

Способы получить реквизит документа

ВЫРАЗИТЬ + обращение через точку

Подходит, когда нужен один-два реквизита. Минус: множит соединения при обращении к нескольким полям, для каждого поля формируется отдельное обращение к таблице.

Левое соединение с таблицей документа

Удобно, когда нужно много реквизитов одного документа. Минус: для каждого вида документа нужно отдельное соединение.

ВЫБОР + ССЫЛКА + ВЫРАЗИТЬ

Подходит для нескольких видов документов с одинаковым реквизитом. Минус: громоздкий текст запроса при большом числе типов.

ВЫРАЗИТЬ в отборах, параметрах и настройках СКД

Приведённое выражение можно использовать не только в списке полей. В секции ГДЕ допустимо условие вида:

ГДЕ

ВЫРАЗИТЬ(Продажи.Регистратор КАК Документ.РеализацияТоваровУслуг).Склад = &Склад

Однако для отборов, которые пользователь будет менять в настройках отчёта, удобнее вычислить поле в запросе (дать ему псевдоним) и вынести его в список доступных полей СКД. Тогда отбор настраивается визуально, без правки запроса.

Ещё одно применение — приведение параметра. Если параметр объявлен составного типа, а сравнивать его нужно с реквизитом конкретного документа, в запросе пишут ВЫРАЗИТЬ(&Документ КАК Документ.ЗаказКлиента). Это снимает неоднозначность типов при сравнении.

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

Каждое обращение вида ВЫРАЗИТЬ(...).Реквизит фактически порождает обращение к таблице документа. Если в запросе десять таких выражений к одному документу, платформа может сформировать несколько соединений с одной и той же таблицей, что замедляет выполнение на больших объёмах.

Практические рекомендации:

  • нужно больше двух-трёх реквизитов одного документа — переходите на явное левое соединение с таблицей документа;
  • не применяйте ВЫРАЗИТЬ к полям, по которым идёт группировка, без необходимости: группировка по выражению обычно тяжелее, чем по исходной ссылке;
  • фильтруйте данные до приведения: сначала ограничьте выборку периодом и измерениями, потом обращайтесь к реквизитам документов;
  • в виртуальных таблицах регистров используйте параметры (период, условия), чтобы уменьшить объём обрабатываемых записей.

Как проверить результат

После добавления ВЫРАЗИТЬ пройдите контрольные точки:

  • конструктор запроса не выдаёт ошибок при нажатии «ОК» — значит, имена документа и реквизитов указаны верно;
  • в отчёте по строкам с нужным видом документа реквизит заполнен, а по строкам с другими документами пуст — это нормальное поведение, а не ошибка;
  • итоговые суммы по количеству и суммам не изменились по сравнению с вариантом без приведения — соединение не задвоило строки;
  • отбор по новому полю в настройках СКД отрабатывает и не приводит к пустому отчёту при корректном значении.

Если поле оказалось пустым для всех строк, первым делом проверьте, тот ли вид документа указан: посмотрите тип регистратора в самих данных (например, через структуру регистра в конфигураторе).

Контрольные точки

Как проверить результат

Заполнение реквизита
Норма

Заполнен у строк с нужным видом документа, NULL у остальных

Тревожный признак

Пусто у всех строк — неверный вид документа или реквизит

Итоги отчёта
Норма

Суммы совпадают с контрольным отчётом без приведения

Тревожный признак

Суммы выросли — соединение задвоило строки

Проверка запроса в конструкторе
Норма

Конструктор принимает текст без сообщений об ошибках

Тревожный признак

Ошибка в имени документа или реквизита

Типичные ошибки

Самая частая ошибка — обращение к реквизиту составного поля без ВЫРАЗИТЬ. Запрос либо не проходит проверку, либо СКД молча возвращает пустые значения, и пользователь получает отчёт с пустой колонкой «Контрагент».

Вторая группа ошибок связана с ожиданиями от данных: разработчик приводит регистратор к одному виду документа и забывает, что движения делают и другие документы. Строки «чужих» документов остаются в отчёте с пустыми реквизитами, а если добавить внутреннее соединение вместо левого — эти строки пропадут вовсе, и итоги перестанут сходиться с типовыми отчётами.

Третья ошибка — приведение к типу, которого нет в составе поля. Например, регистратор регистра никогда не бывает документом «Счёт на оплату», а разработчик указал именно его. Запрос отработает без ошибок, но поле будет всегда NULL.

Типичные ошибки
01
Обращение Регистратор.Реквизит без ВЫРАЗИТЬ — ошибка проверки запроса или пустые значения в отчёте
02
Приведение только к одному виду документа при нескольких реальных регистраторах — часть строк получает NULL и выпадает из анализа
03
Внутреннее соединение с таблицей документа вместо левого — строки с другими документами исчезают, итоги расходятся
04
Опечатка в имени документа в тексте, набранном вручную вне конструктора, — ошибка обнаруживается только при выполнении отчёта

Итог

Приведение поля к документу в СКД делается оператором ВЫРАЗИТЬ в тексте запроса набора данных. Для одного-двух реквизитов достаточно ВЫРАЗИТЬ(Поле КАК Документ.Имя).Реквизит, для нескольких реквизитов выгоднее левое соединение с таблицей документа, а для нескольких видов документов — конструкция ВЫБОР с проверкой ССЫЛКА. После правки обязательно сверьте итоги отчёта с контрольным вариантом и проверьте заполнение полей на строках с разными регистраторами.

Итог

Что важно запомнить

ВЫРАЗИТЬ(Поле КАК Документ.Имя) открывает доступ к реквизитам документа через составное поле. Для строк с другим типом результат — NULL. Много реквизитов — используйте соединение, несколько видов документов — ВЫБОР с проверкой ССЫЛКА. Всегда сверяйте итоги после изменения запроса.

Частые вопросы

Можно ли выразить поле как документ не в запросе, а в настройках СКД?

Нет, оператор ВЫРАЗИТЬ доступен только в языке запросов. В вычисляемых полях СКД и выражениях ресурсов он не поддерживается — там работает собственный язык выражений компоновки. Поэтому приведение всегда выполняется в тексте запроса набора данных, а в настройки выносится уже готовое поле с псевдонимом.

Почему после ВЫРАЗИТЬ поле пустое у всех строк?

Чаще всего указан не тот вид документа, который реально записан в поле. Откройте регистратор в данных и проверьте его тип. Вторая причина — ошибка в имени реквизита: запрос может пройти проверку, если имя совпадает со стандартным реквизитом, но не с тем, что нужен вам. Третья — поле изначально имеет не ссылочный тип, тогда приведение к документу всегда даст NULL.

Чем отличается ВЫРАЗИТЬ от проверки ССЫЛКА?

ВЫРАЗИТЬ приводит значение к типу и позволяет обращаться к реквизитам, а оператор ССЫЛКА только проверяет принадлежность значения к типу и возвращает Истина или Ложь. Обычно их комбинируют: ССЫЛКА — в условии ВЫБОР, ВЫРАЗИТЬ — в ветке ТОГДА для доступа к реквизиту.

Можно ли выразить строку или число как документ?

Нет. Приведение возможно только между совместимыми типами: ссылочное поле составного типа — к конкретному ссылочному типу. Строку с наименованием или номером документа нельзя «превратить» в ссылку оператором ВЫРАЗИТЬ — результатом будет NULL. Для поиска ссылки по номеру потребуется соединение с таблицей документа по полю «Номер».

Влияет ли ВЫРАЗИТЬ на скорость отчёта?

Да, обращение к реквизитам через приведённое поле добавляет обращения к таблицам документов. На небольших выборках это незаметно, на больших — может существенно замедлить выполнение. Чтобы снизить нагрузку, ограничивайте выборку параметрами виртуальных таблиц, а при необходимости нескольких реквизитов заменяйте множественные ВЫРАЗИТЬ одним соединением.

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

Одним ВЫРАЗИТЬ это сделать нельзя — целевой тип указывается один. Используйте ВЫБОР с последовательными проверками ССЫЛКА и отдельным ВЫРАЗИТЬ в каждой ветке, либо несколько левых соединений с таблицами нужных документов и сбор значения через ЕСТЬNULL(Таб1.Реквизит, Таб2.Реквизит).