Разработка и Конфигурация · 12 мин
Для чего нужны перечисления в 1С
Зачем нужны перечисления в 1С: отличия от справочников, типовые сценарии использования, примеры кода, ограничения и типичные ошибки разработчиков.
Перечисление в 1С — это объект метаданных, который хранит жёстко зафиксированный список значений, определённых ещё на этапе разработки конфигурации. В отличие от справочника, пользователь не может добавить в перечисление новый элемент через интерфейс: состав значений меняется только в конфигураторе. Именно это свойство делает перечисления удобным инструментом для описания статусов, видов операций, ставок НДС и других величин, набор которых определяется логикой программы, а не данными предприятия.
Типичный пример — ставки налога на добавленную стоимость. Законодательно возможны только определённые варианты (20%, 10%, 0%, без НДС), и позволять бухгалтеру вводить произвольное значение нельзя: любая опечатка приведёт к ошибкам в отчётности. Перечисление «СтавкиНДС» решает задачу: пользователь выбирает значение из выпадающего списка, а программа гарантированно работает только с допустимыми вариантами.
Понимание назначения перечислений важно и при чтении типовых конфигураций, и при проектировании собственных решений. Неверный выбор между перечислением и справочником — одна из самых частых архитектурных ошибок начинающих разработчиков: она либо блокирует расширение данных пользователем, либо, наоборот, позволяет испортить критичные для алгоритмов значения.
Что представляет собой перечисление и как оно устроено
Перечисление создаётся в ветке «Перечисления» дерева конфигурации. У объекта есть имя, синоним и набор значений, каждое из которых также имеет имя (идентификатор для кода) и синоним (представление для пользователя). Например, значение «НДС20» может отображаться как «20%». Разделение имени и представления позволяет менять отображаемый текст без правки алгоритмов.
В базе данных значение перечисления хранится компактно — фактически как порядковый номер внутри списка. Это делает сравнения и отборы по перечислению быстрыми, а объём занимаемого места — минимальным. Каждое значение доступно в коде через менеджер перечисления: Перечисления.СтавкиНДС.НДС20.
Перечисление может использоваться как тип реквизита документов, справочников, регистров и других объектов. В форме такой реквизит отображается как выпадающий список или поле с выбором, что исключает ввод произвольного текста.
Основные задачи, которые решают перечисления
Первая задача — фиксация допустимых вариантов. Если бизнес-правило допускает конечный и известный заранее набор вариантов (пол сотрудника, периодичность планирования, способ округления, вид цены), перечисление гарантирует, что в базе не появится значение, которое алгоритмы не умеют обрабатывать.
Вторая задача — читаемость кода. Конструкция Если Документ.ВидОперации = Перечисления.ВидыОпераций.Продажа Тогда понятна любому разработчику, тогда как сравнение с магическими числами или строками («Если Вид = 2 Тогда») требует расшифровки и легко ломается при правках.
Третья задача — построение развилок в логике. По значению перечисления удобно организовывать ветвление: проводить документ по-разному в зависимости от вида операции, формировать разные движения, подставлять разные счета учёта. Перечисление становится переключателем поведения программы.
Четвёртая задача — согласованность между объектами. Одно и то же перечисление может быть реквизитом десятков документов и регистров. Все они ссылаются на единый набор значений, поэтому отборы, группировки в отчётах и соединения в запросах работают корректно без сопоставления текстовых представлений.
Когда выбирать перечисление, а когда справочник
Ключевой критерий — кто управляет составом значений. Если набор определяется логикой программы и меняется только вместе с обновлением конфигурации, нужен перечисление. Если пользователи должны добавлять, переименовывать и удалять элементы самостоятельно (контрагенты, номенклатура, склады, подразделения) — только справочник.
Второй критерий — зависимость кода от конкретных значений. Если в алгоритмах есть ветвление вида «если статус равен X, делай одно, если Y — другое», значения должны быть неизменяемы, иначе пользователь удалит элемент и сломает логику. Это однозначно сценарий для перечисления.
Сравнение вариантов
Подходит для фиксированных наборов: статусов, видов операций, ставок. Значения меняются только разработчиком. Ограничение: нельзя добавить значение в режиме предприятия.
Подходит для данных, которыми управляет пользователь: контрагенты, товары, договоры. Поддерживает иерархию и дополнительные реквизиты. Ограничение: пользователь может удалить или переименовать элемент, на который опирается код.
Допустимо только для свободных данных без ограничений. Не подходит для статусов и видов: опечатки и разнобой в написании разрушают отборы и отчёты.
Промежуточный вариант — предопределённые элементы справочника. Они создаются разработчиком, доступны в коде по имени, но справочник остаётся открытым для пользовательских элементов. Такой подход применяют, когда часть значений критична для алгоритмов, а часть должна расширяться пользователем. Например, виды контактной информации: обязательные виды заданы разработчиком, дополнительные добавляют пользователи.
Как выбрать действие
Как добавить перечисление и использовать его в коде
Создание перечисления занимает несколько минут в конфигураторе. После этого его можно назначать типом реквизитов и использовать в модулях. Порядок действий стандартный и не зависит от конкретной конфигурации.
- 1Откройте конфигуратор, в дереве конфигурации найдите ветку «Перечисления» и добавьте новый объект
- 2Задайте имя (латиницей, без пробелов) и синоним — он будет виден пользователям
- 3На закладке «Данные» добавьте значения: у каждого укажите имя и синоним
- 4Создайте реквизит нужного объекта (документа, справочника) и назначьте ему тип — созданное перечисление
- 5Обновите конфигурацию базы данных (F7) и проверьте, что в форме реквизит отображается как список выбора
В коде значения перечисления доступны через менеджер. Типичные приёмы — сравнение, ветвление и получение представления значения:
Если Заказ.Статус = Перечисления.СтатусыЗаказа.ВРаботе Тогда
// логика обработки заказа в работе
ИначеЕсли Заказ.Статус = Перечисления.СтатусыЗаказа.Закрыт Тогда
// закрытый заказ редактировать нельзя
КонецЕсли;
Представление = Строка(Заказ.Статус); // "В работе"
В запросах значения перечисления передаются как параметры. Прямое сравнение с перечислением в тексте запроса тоже возможно через оператор ЗНАЧЕНИЕ: ГДЕ Статус = ЗНАЧЕНИЕ(Перечисление.СтатусыЗаказа.Закрыт). Это удобно для отборов в отчётах и динамических списках.
Ограничения перечислений, о которых нужно помнить
Главное ограничение — закрытость списка. Если бизнес-процесс требует нового значения, придётся править конфигурацию и обновлять базу. Для часто меняющихся наборов это неприемлемо: каждое изменение требует участия разработчика и монопольного доступа при обновлении.
Второе ограничение — у значений перечисления нет дополнительных свойств. Нельзя хранить, например, числовую ставку рядом со значением «НДС20» — соответствие придётся зашивать в код функциями вида «ПолучитьСтавкуНДС». Если значениям нужны атрибуты, правильный выбор — справочник.
Третий риск — изменение порядка значений. Значения хранятся в базе по порядковому номеру, поэтому вставка нового значения в середину списка при обновлении конфигурации может «сдвинуть» существующие данные: документы со старым значением начнут отображать другое. Безопасное правило — новые значения добавлять только в конец списка и никогда не удалять используемые.
Типичные ошибки при работе с перечислениями
Начинающие разработчики регулярно повторяют одни и те же ошибки. Знание их заранее экономит часы отладки и защищает данные от порчи.
Отдельная ошибка — игнорирование пустого значения. Если реквизит типа «перечисление» не заполнен, он содержит пустую ссылку, и ветвление по значениям его не покроет. Всегда обрабатывайте случай незаполненного реквизита явно, особенно при проведении документов.
Как проверить результат
Отображается как выпадающий список с заданными синонимами значений
Поле позволяет вводить произвольный текст или список пуст
Показывают те же значения, что и до обновления конфигурации
Значения «съехали» или стали пустыми — порядок значений был нарушен
Сравнение идёт через Перечисления.Имя.Значение, обработан случай пустого значения
Сравнение со строкой или числом, ветка для пустого значения отсутствует
Практические рекомендации по проектированию
Проектируйте перечисление как часть предметной модели: имена значений должны отражать смысл, а не текущую формулировку интерфейса. Синонимы можно менять свободно, имена — крайне нежелательно, потому что на них завязан код и, возможно, внешние обмены.
Для статусов объектов полезно закладывать значение «по умолчанию» первым в списке и явно присваивать его при создании объекта. Это избавляет от ситуации, когда новый документ остаётся с пустым статусом и выпадает из всех отборов.
Если перечисление участвует в обмене данными с внешними системами, зафиксируйте соответствие значений внешним кодам в одном месте — функции сопоставления. Разбросанные по модулям сравнения усложняют сопровождение при изменении формата обмена.
Что важно запомнить
Перечисления хранят фиксированные наборы значений, заданные разработчиком, и защищают данные от произвольного ввода. Выбирайте перечисление, когда набор значений определяется логикой программы; справочник — когда значениями управляют пользователи. Новые значения добавляйте только в конец списка и никогда не удаляйте используемые, иначе пострадают существующие данные.
Частые вопросы
Может ли пользователь добавить значение в перечисление без программиста?
Нет. Состав перечисления меняется только в конфигураторе с последующим обновлением конфигурации базы данных. Если пользователям нужно самостоятельно расширять список, используйте справочник — обычный или с предопределёнными элементами для критичных значений.
Что произойдёт, если удалить значение перечисления, которое используется в документах?
В существующих записях останется порядковый номер, которому больше не соответствует значение, — реквизит станет пустым или некорректным. Алгоритмы, рассчитывающие на это значение, перестанут обрабатывать такие документы. Перед удалением значения найдите все ссылки на него и переведите данные на другое значение.
Можно ли хранить у значения перечисления дополнительные данные, например числовую ставку?
Нет, у значений перечисления нет реквизитов. Связанные данные придётся хранить в коде (функции сопоставления) или в отдельном регистре сведений. Если атрибуты значений должны редактироваться пользователями, замените перечисление справочником.
Как сослаться на значение перечисления в запросе?
Двумя способами: передать значение параметром (ГДЕ Статус = &Статус) или использовать литерал ЗНАЧЕНИЕ(Перечисление.ИмяПеречисления.ИмяЗначения) прямо в тексте запроса. Оба варианта корректны; параметр предпочтителен, когда значение выбирается динамически.
Чем перечисление отличается от предопределённых элементов справочника?
Предопределённые элементы тоже доступны в коде по имени, но справочник остаётся открытым: пользователь может добавлять свои элементы и, при отсутствии запретов, менять предопределённые. Перечисление полностью закрыто. Выбор зависит от того, нужно ли пользователям расширять список.
Почему после обновления конфигурации в документах «съехали» значения перечисления?
Почти всегда причина — вставка нового значения в середину списка или изменение порядка значений. В базе хранится порядковый номер, и после сдвига он указывает на другое значение. Восстановите порядок из резервной копии конфигурации и добавляйте новые значения только в конец списка.