Разработка и Конфигурация · 11 мин
Как создать функцию в 1С: полное руководство для разработчика
Пошаговая инструкция: как создать функцию в 1С, где разместить её в общем модуле, как передать параметры, вернуть значение и избежать типичных ошибок.
Функция во встроенном языке 1С — это именованный блок кода, который принимает параметры, выполняет вычисления и обязательно возвращает результат. В отличие от процедуры, функцию можно использовать прямо в выражениях: присваивать её результат переменной, передавать в другие функции, подставлять в условия. Понимание того, как правильно создавать функции и где их размещать, — базовый навык для любой доработки конфигурации.
Функции создаются в модулях: общих модулях, модулях объектов, модулях форм, модулях менеджеров. Выбор места размещения определяет, откуда функция будет доступна и на какой стороне — клиенте или сервере — она выполнится. Ошибка с размещением — одна из самых частых причин сообщений вида «Процедура или функция с указанным именем не определена».
Ниже разобран полный цикл работы: от создания общего модуля и написания функции до её вызова, отладки и проверки результата. Примеры приведены для управляемого приложения, но синтаксис идентичен и в обычных формах.
Чем функция отличается от процедуры и когда что выбирать
Функция всегда возвращает значение через оператор Возврат, и это значение можно использовать в выражениях. Процедура ничего не возвращает — она просто выполняет действия: записывает данные, открывает форму, выводит сообщение. Если результат выполнения кода нужен вызывающей стороне (сумма скидки, признак проверки, найденная ссылка), нужна функция.
Типичный признак того, что выбран неверный тип: вы написали процедуру, а потом вынуждены передавать результат через параметр по ссылке или через глобальную переменную. Это усложняет код и провоцирует ошибки. Перепишите такой блок как функцию с явным возвратом значения.
Функция или процедура
Нужен результат вычисления: сумма, признак, ссылка, структура данных. Результат используется в выражениях и присваиваниях.
Нужно только действие без результата: запись объекта, вывод сообщения, открытие формы, запуск обработки.
Где разместить функцию: выбор модуля
Место размещения определяет область видимости. Если функция нужна только внутри одной формы или одного документа — пишите её прямо в модуле формы или объекта без слова Экспорт. Если функция должна вызываться из разных объектов конфигурации — создайте или используйте существующий общий модуль.
У общего модуля критически важны флаги в палитре свойств. Флаг «Сервер» означает выполнение на сервере, «Клиент (управляемое приложение)» — на клиенте. Код, работающий с базой данных (запросы, записи объектов), должен выполняться на сервере. Если функция с запросом окажется в клиентском модуле, при вызове получите ошибку компиляции или выполнения.
Также учитывайте флаг «Привилегированный режим»: он отключает проверку прав доступа для кода модуля. Включайте его осознанно — функция в таком модуле сможет читать и изменять данные, к которым у текущего пользователя нет прав. Для большинства прикладных функций этот флаг не нужен.
Создание общего модуля и написание функции
Откройте конфигуратор, в дереве конфигурации найдите ветку «Общие» → «Общие модули» и добавьте новый модуль, например РаботаСоСкидками. В палитре свойств установите флаг «Сервер». Если функции будут вызываться из клиентского кода, дополнительно включите «Вызов сервера».
В теле модуля напишите функцию. Минимальный рабочий пример — расчёт суммы скидки по проценту:
Функция РассчитатьСкидку(СуммаДокумента, ПроцентСкидки) Экспорт
Если ПроцентСкидки < 0 Или ПроцентСкидки > 100 Тогда
ВызватьИсключение "Процент скидки должен быть от 0 до 100";
КонецЕсли;
СуммаСкидки = СуммаДокумента * ПроцентСкидки / 100;
Возврат СуммаСкидки;
КонецФункции
Разберём конструкцию. Ключевое слово Функция открывает объявление, далее идут имя и в скобках список параметров. Слово Экспорт делает функцию доступной из других модулей — без него вызов снаружи будет невозможен. Оператор Возврат завершает выполнение и передаёт значение вызывающему коду. Завершает объявление КонецФункции.
- 1В конфигураторе создайте общий модуль и установите нужные флаги (Сервер, Вызов сервера)
- 2Напишите функцию: имя, параметры, слово Экспорт, тело с обязательным Возврат
- 3Проверьте синтаксис: Ctrl+F7 или пункт меню «Конфигурация — Проверка конфигурации»
- 4Обновите конфигурацию базы данных (F7), если изменения этого требуют
- 5Вызовите функцию из прикладного кода и проверьте результат в отладчике
Параметры: передача по значению и по ссылке
По умолчанию параметры передаются по ссылке: изменения параметра внутри функции видны снаружи. Если добавить перед именем параметра слово Знач, передача пойдёт по значению — функция получит копию, и оригинальная переменная вызывающего кода не изменится. Для функций передача по значению предпочтительнее: она делает поведение предсказуемым.
Параметру можно задать значение по умолчанию: Функция РассчитатьСкидку(СуммаДокумента, ПроцентСкидки = 0) Экспорт. Тогда функцию можно вызвать с одним аргументом. Параметры со значениями по умолчанию должны стоять в конце списка.
Проверяйте входные данные в начале функции. Если параметр обязателен и его отсутствие делает вычисление бессмысленным, вызывайте исключение с понятным текстом, как в примере выше. Молчаливая обработка некорректных данных приводит к ошибкам, которые всплывут гораздо позже и в другом месте.
Вызов функции и проверка результата
Функцию из общего модуля вызывают через имя модуля: СуммаСкидки = РаботаСоСкидками.РассчитатьСкидку(ИтогСумма, 10);. Если функция объявлена в том же модуле, где вызывается, имя модуля не нужно — достаточно имени функции.
Для проверки используйте отладчик: поставьте точку останова (F9) на строке вызова, запустите отладку (F5), шагните внутрь функции (F11) и посмотрите значения переменных в табло. Контрольный пример: при сумме 10 000 и проценте 15 результат должен быть 1 500. Если значение отличается — проблема в формуле или в входных данных.
Как проверить результат
На всех ветках логики выполняется оператор Возврат, значение имеет ожидаемый тип
Есть путь выполнения без Возврат — функция вернёт Неопределено
Вызов из другого модуля компилируется без ошибок, функция объявлена с Экспорт
Ошибка «Процедура или функция с указанным именем не определена»
Серверный код (запросы, записи) находится в серверном модуле
Ошибка о недопустимости вызова на клиенте или отсутствии контекста
Типичные ошибки при создании функций
Самая распространённая ошибка — отсутствие Возврат на одной из веток условной логики. Например, возврат написан внутри Если, а для ветки Иначе забыт. В этом случае функция вернёт Неопределено, и вызывающий код получит непредсказуемое значение. Проверяйте, что каждый путь выполнения заканчивается возвратом.
Вторая группа ошибок связана с контекстом: функция с запросом к базе размещена в клиентском модуле, либо клиентская функция пытается напрямую вызвать серверную без флага «Вызов сервера». Третья типичная проблема — забытое слово Экспорт, из-за которого функция невидима снаружи модуля.
Расширенные сценарии: директивы компиляции и возврат сложных данных
Если функция находится в модуле формы и должна выполняться на сервере, перед ней указывают директиву &НаСервере. Для клиентского кода — &НаКлиенте. Функция, вызываемая и там и там, помечается &НаСервереБезКонтекста, если ей не нужны данные формы. В общих модулях директивы не нужны — контекст задаётся флагами модуля.
Возврат нескольких значений
Функция возвращает одно значение, но это может быть структура или массив. Например, функция анализа документа может вернуть структуру с полями «ЕстьОшибки», «ТекстОшибки», «СуммаРасхождения». Это чище, чем передавать несколько параметров по ссылке для возврата результатов.
Функции в расширениях конфигурации
Если конфигурация на поддержке и менять её нельзя, функции добавляют через расширение: создайте расширение, добавьте в него собственный общий модуль и разместите функции там. Это безопаснее прямой доработки: расширение не мешает обновлению конфигурации поставщика.
Давайте функциям говорящие имена по шаблону «глагол + объект»: РассчитатьСкидку, ПолучитьОстаток, ПроверитьЗаполнение. По такому имени сразу понятно, что функция делает и что возвращает, а код читается без комментариев.
Частые вопросы
Чем отличается слово Экспорт у функции?
Экспорт делает функцию видимой за пределами текущего модуля. Без него функцию можно вызвать только из того же модуля. Для функций в общих модулях, предназначенных для вызова из прикладного кода, Экспорт обязателен.
Почему возникает ошибка «Процедура или функция с указанным именем не определена»?
Основные причины: забыто слово Экспорт, опечатка в имени функции или модуля, общий модуль недоступен в текущем контексте (например, серверный модуль вызывается с клиента без флага «Вызов сервера»), либо изменения не обновлены в конфигурации базы данных.
Может ли функция ничего не возвращать?
Формально оператор Возврат можно написать без значения — тогда функция вернёт Неопределено. Но если результат не нужен, правильнее оформить код как процедуру: это честно отражает назначение блока и упрощает чтение.
Как вызвать серверную функцию из клиентского кода формы?
Разместите функцию в общем модуле с флагами «Сервер» и «Вызов сервера». Из клиентской процедуры формы вызовите её по имени модуля. Учтите: каждый такой вызов — это обращение к серверу, поэтому не вызывайте серверные функции в циклах, лучше собрать данные одним вызовом.
Нужно ли описывать типы параметров функции?
Встроенный язык 1С — с динамической типизацией, явного объявления типов параметров нет. Типы фиксируют в комментарии перед функцией (так называемое описание для синтакс-помощника EDT/конфигуратора), а внутри функции при необходимости проверяют через ТипЗнч().
Где лучше хранить функции: в одном большом модуле или в нескольких?
Группируйте функции по прикладному смыслу: отдельные модули для работы со скидками, с номенклатурой, с печатью. Один «сводный» модуль на всё затрудняет поиск и увеличивает риск конфликтов при командной разработке.
Что важно запомнить
Функция создаётся конструкцией Функция...Экспорт...Возврат...КонецФункции в подходящем модуле. Общие модули настраиваются флагами контекста (Сервер, Клиент, Вызов сервера). Контролируйте три вещи: наличие Возврат на всех ветках, слово Экспорт для внешнего вызова и соответствие кода контексту выполнения. Проверяйте результат в отладчике на контрольных данных.