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

Разработка и Конфигурация · 13 мин

ВЫБОР КОГДА с перечислением в запросе 1С: синтаксис, примеры и ошибки

Как использовать ВЫБОР КОГДА с перечислением в запросе 1С: синтаксис, сравнение со значением перечисления, проверка пустых ссылок, типовые ошибки и примеры кода.

Конструкция ВЫБОР КОГДА в языке запросов 1С — это аналог оператора CASE в SQL. Она позволяет вернуть разные значения в зависимости от условий, и одна из самых частых задач — сопоставить поле типа «ПеречислениеСсылка» с конкретным значением и вывести текст, число или другую ссылку. Например, в отчёте по документам нужно показать «Оплачен» или «Не оплачен» вместо служебного значения перечисления «СтатусОплаты».

Главная сложность при работе с перечислениями в запросе — правильное обращение к значению. В отличие от встроенного языка, где пишут Перечисления.СтавкиНДС.НДС20, в тексте запроса используется функция ЗНАЧЕНИЕ(Перечисление.СтавкиНДС.НДС20) — без буквы «и» после «Перечисление» и через конструкцию ЗНАЧЕНИЕ. Ошибка в этой детали — самая частая причина того, что запрос не выполняется или возвращает пустой результат.

Ниже разобраны синтаксис ВЫБОР КОГДА, способы сравнения с перечислением, работа с пустыми ссылками, альтернатива через СОЕДИНЕНИЕ, типичные ошибки и способы проверить результат до вывода в отчёт.

Синтаксис ВЫБОР КОГДА в языке запросов 1С

Общая форма конструкции выглядит так: после ключевого слова ВЫБОР перечисляются ветки КОГДА с условием и результатом через ТОГДА, в конце — необязательная ветка ИНАЧЕ и обязательное слово КОНЕЦ. Условий может быть сколько угодно, они проверяются сверху вниз, и срабатывает первая истинная ветка.

ВЫБОР

КОГДА Документ.Статус = ЗНАЧЕНИЕ(Перечисление.СтатусыДокумента.Проведен)

ТОГДА "Проведён"

КОГДА Документ.Статус = ЗНАЧЕНИЕ(Перечисление.СтатусыДокумента.Отклонен)

ТОГДА "Отклонён"

ИНАЧЕ "В работе"

КОНЕЦ КАК СтатусТекстом

Важные правила синтаксиса. Все возвращаемые значения в ветках ТОГДА и ИНАЧЕ должны быть совместимы по типу: нельзя в одной ветке вернуть строку, а в другой — число или ссылку, иначе получите ошибку несовместимости типов или непредсказуемый результат в СКД. Если ветка ИНАЧЕ отсутствует и ни одно условие не сработало, поле получит значение NULL — это нужно учитывать при последующей группировке и соединениях.

Псевдоним поля задаётся через КАК после слова КОНЕЦ. Без псевдонима обратиться к вычисляемой колонке в коде или настройках СКД будет затруднительно.

Как правильно сослаться на значение перечисления

Ключевое отличие запроса от встроенного языка — написание. В модуле вы обращаетесь к менеджеру Перечисления (множественное число), а в тексте запроса — к типу Перечисление (единственное число) внутри функции ЗНАЧЕНИЕ. Полная форма: ЗНАЧЕНИЕ(Перечисление.ИмяПеречисления.ИмяЗначения).

ГДЕ

Товары.СтавкаНДС = ЗНАЧЕНИЕ(Перечисление.СтавкиНДС.НДС20)

Имя значения в запросе — это имя, заданное в конфигураторе, а не синоним, который видит пользователь. Если значение называется «НДС20», а синоним — «20%», в запросе пишется именно «НДС20». Посмотреть имя можно в конфигураторе: откройте перечисление в дереве метаданных и проверьте колонку «Имя» у нужного значения.

Альтернатива — передать значение параметром: ГДЕ Товары.СтавкаНДС = &Ставка, а в коде установить Запрос.УстановитьПараметр("Ставка", Перечисления.СтавкиНДС.НДС20). Параметр удобнее, когда значение выбирает пользователь или оно вычисляется в коде, а ЗНАЧЕНИЕ — когда условие жёстко зашито в текст запроса. Параметр также делает запрос устойчивым к переименованию значений перечисления в конфигурации.

ЗНАЧЕНИЕ или параметр

ЗНАЧЕНИЕ(Перечисление... )

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

Параметр &Имя

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

Сравнение поля с перечислением внутри ВЫБОР КОГДА

Самый частый сценарий — преобразовать значение перечисления в понятную строку или в другое представление для отчёта. Условие в ветке КОГДА — обычное сравнение поля через знак равенства со значением перечисления.

ВЫБОР

КОГДА Реализация.ВидОперации = ЗНАЧЕНИЕ(Перечисление.ВидыОперацийРеализация.Товары)

ТОГДА "Продажа товаров"

КОГДА Реализация.ВидОперации = ЗНАЧЕНИЕ(Перечисление.ВидыОперацийРеализация.Услуги)

ТОГДА "Продажа услуг"

ИНАЧЕ "Прочее"

КОНЕЦ КАК ОписаниеОперации

В условии допустимы и другие операторы: неравенство <>, проверка В ИЕРАРХИИ (для перечислений не применяется, так как они не иерархические), логические И и ИЛИ для комбинации нескольких условий. Например, можно объединить проверку перечисления с проверкой суммы документа в одной ветке.

Учтите порядок веток: если условия пересекаются, сработает первая по тексту. Поэтому более частные условия ставьте выше, а общие — ниже. Ветка ИНАЧЕ в конце страхует от появления NULL при добавлении в конфигурацию новых значений перечисления, которые ваш запрос ещё не обрабатывает.

Порядок действий
  1. 1
    Откройте перечисление в конфигураторе и выпишите точные имена нужных значений (колонка «Имя», не синоним).
  2. 2
    Сформируйте текст запроса: ВЫБОР КОГДА Поле = ЗНАЧЕНИЕ(Перечисление.Имя.Значение) ТОГДА ... ИНАЧЕ ... КОНЕЦ КАК Псевдоним.
  3. 3
    Убедитесь, что все ветки ТОГДА и ИНАЧЕ возвращают значения одного типа.
  4. 4
    Выполните запрос в консоли запросов на тестовой копии базы и проверьте, что каждая ветка срабатывает на реальных данных.
  5. 5
    Перенесите проверенный текст в модуль или схему СКД.

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

Если реквизит типа «ПеречислениеСсылка» не заполнен, он хранит пустую ссылку, а не NULL. Поэтому проверка Поле ЕСТЬ NULL такой случай не поймает. Пустую ссылку сравнивают с пустым значением перечисления: ЗНАЧЕНИЕ(Перечисление.ИмяПеречисления.ПустаяСсылка).

ВЫБОР

КОГДА Документ.Статус = ЗНАЧЕНИЕ(Перечисление.СтатусыДокумента.ПустаяСсылка)

ТОГДА "Статус не задан"

КОГДА Документ.Статус = ЗНАЧЕНИЕ(Перечисление.СтатусыДокумента.Завершен)

ТОГДА "Завершён"

ИНАЧЕ "В работе"

КОНЕЦ КАК СтатусТекстом

NULL в поле типа перечисления появляется только в результате соединений таблиц — например, при ЛЕВОМ СОЕДИНЕНИИ, когда в правой таблице нет подходящей строки. В этом случае проверка Поле ЕСТЬ NULL обязательна, и её стоит ставить первой веткой, потому что сравнение NULL с чем-либо через равенство всегда даёт ложь.

Рабочая последовательность веток для поля из соединения: сначала КОГДА Поле ЕСТЬ NULL ТОГДА ..., затем проверка пустой ссылки, затем конкретные значения, в конце ИНАЧЕ. Такой порядок гарантирует, что ни одна ситуация не выпадет в NULL результата.

Альтернатива: СОЕДИНЕНИЕ с таблицей перечисления

Если нужно не сопоставить значения вручную, а просто вывести представление перечисления или отобрать по нему, можно соединиться с виртуальной таблицей перечисления: Перечисление.ИмяПеречисления. У неё есть поля Ссылка, Порядок и Представление.

ВЫБРАТЬ

Документы.Ссылка,

Статусы.Представление КАК СтатусПредставление

ИЗ

Документ.ЗаказКлиента КАК Документы

ЛЕВОЕ СОЕДИНЕНИЕ Перечисление.СтатусыЗаказа КАК Статусы

ПО Документы.Статус = Статусы.Ссылка

Этот способ удобен, когда нужно вывести все возможные значения перечисления (даже те, которых нет в документах) — для этого перечисление ставят первой таблицей и делают ЛЕВОЕ СОЕДИНЕНИЕ документов к нему. Также поле Порядок позволяет сортировать по порядку значений в конфигураторе, а не по алфавиту представления.

Однако для логики «если статус такой-то, то вывести такой-то текст» соединение не заменяет ВЫБОР КОГДА: произвольные соответствия, отличные от синонимов, всё равно задаются только ветками КОГДА.

Типичные ошибки и как их найти

Первая и самая массовая ошибка — написать Перечисления.Имя.Значение (во множественном числе) или забыть обёртку ЗНАЧЕНИЕ. Конструктор запросов при проверке выдаст сообщение о неверном поле или типе. Вторая ошибка — использовать синоним значения вместо имени: запрос выполнится с ошибкой «Поле не найдено», потому что платформа ищет именно имя метаданных.

Третья группа ошибок связана с типами результата: в одной ветке строка, в другой — число или ссылка. В простом запросе это иногда проходит незамеченным, но в СКД или при помещении результата во временную таблицу приводит к ошибкам приведения типов. Четвёртая ошибка — забыть ИНАЧЕ и получить NULL, который затем «съедает» строки при внутреннем соединении по этому полю или ломает итоги группировки.

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

Типичные ошибки
01
Написать «Перечисления» во множественном числе или опустить ЗНАЧЕНИЕ — запрос не выполнится с ошибкой синтаксиса или типа.
02
Использовать синоним значения вместо имени из конфигуратора — платформа сообщит, что поле не найдено.
03
Вернуть в разных ветках разные типы (строку и число) — ошибки при выводе в СКД или временную таблицу.
04
Забыть ветку ИНАЧЕ — при новых значениях перечисления в поле появится NULL, что ломает соединения и группировки.
05
Проверять незаполненный реквизит через ЕСТЬ NULL вместо сравнения с ПустаяСсылка — условие никогда не сработает.

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

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

Если запрос используется в отчёте на СКД, дополнительно проверьте итоги: NULL в поле группировки создаёт отдельную строку итога с пустым значением, что часто выглядит как «лишняя строка» в отчёте. Лечится веткой ИНАЧЕ или отбором в настройках.

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

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

Колонка результата ВЫБОР КОГДА
Норма

Все строки заполнены ожидаемыми значениями веток

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

Есть NULL или пустые значения там, где их не должно быть

Документ с незаполненным реквизитом-перечислением
Норма

Попадает в ветку проверки ПустаяСсылка или ИНАЧЕ

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

Строка теряется или получает неверное значение

Итоги в отчёте СКД
Норма

Группировки соответствуют заданным веткам

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

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

Можно ли сравнивать перечисление со строкой в запросе 1С?

Напрямую нет: поле типа ПеречислениеСсылка нельзя сравнить со строкой, это разные типы. Если нужно сопоставить с текстом, сравнивайте поле с ЗНАЧЕНИЕ(Перечисление...), а строку возвращайте в ветке ТОГДА. Либо получите представление через соединение с таблицей перечисления и сравнивайте уже поле Представление, но это медленнее и менее надёжно.

Чем ВЫБОР КОГДА отличается от функции ЕСТЬNULL?

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

Что будет, если значение перечисления переименуют в конфигураторе?

Запрос с ЗНАЧЕНИЕ(Перечисление.Имя.СтароеИмя) перестанет выполняться с ошибкой «Поле не найдено». Платформа при реструктуризации не отслеживает тексты запросов в модулях. Чтобы снизить риск, передавайте значение параметром из кода — там переименование отслеживается рефакторингом, либо после переименования выполните поиск старого имени по всем модулям конфигурации.

Можно ли в ТОГДА вернуть ссылку на другое перечисление или справочник?

Да, если во всех ветках возвращается один и тот же тип. Например, все ветки возвращают значения одного перечисления или ссылки одного справочника. Смешивать ссылку и строку нельзя — получите ошибку несовместимости типов при выполнении или в СКД. Если нужны разные типы, приводите всё к строке через ПРЕДСТАВЛЕНИЕ.

Как вывести значение перечисления как число или порядок?

Числового «кода» у значений перечисления нет, но есть поле Порядок в таблице перечисления. Соединитесь с Перечисление.ИмяПеречисления по ссылке и выберите поле Порядок — получите порядковый номер значения, заданный в конфигураторе. Его же удобно использовать для сортировки вместо алфавитного порядка представлений.

Работает ли ВЫБОР КОГДА в условии ГДЕ или только в списке полей?

ВЫБОР КОГДА допустим в списке выбираемых полей, в условии ГДЕ, в ИМЕЮЩИЕ и в условиях соединения. Однако в ГДЕ проще и быстрее писать прямое сравнение: ГДЕ Поле = ЗНАЧЕНИЕ(...). ВЫБОР в отборе оправдан только для сложной логики, которую нельзя выразить простыми условиями с И и ИЛИ.

Итог

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

Значение перечисления в запросе указывается через ЗНАЧЕНИЕ(Перечисление.Имя.Значение) — в единственном числе и по имени из конфигуратора. В ВЫБОР КОГДА все ветки должны возвращать один тип, ветка ИНАЧЕ защищает от NULL, а незаполненный реквизит проверяется сравнением с ПустаяСсылка. Перед использованием в отчёте запрос проверяют в консоли на документах с известными статусами.