При написании или редактировании кода в конфигураторе 1С начинающие разработчики часто сталкиваются с ошибками компиляции, которые могут сбить с толку. Одна из самых распространенных — это сообщение конфигуратора: «Ожидается ключевое слово 'КонецПроцедуры' ('EndProcedure')». Рассмотрим подробнее, почему возникает эта ошибка, как правильно анализировать структуру кода и какие инструменты платформы помогут нам быстро находить незакрытые конструкции.
Разберем по шагам код, который вызывает каскад ошибок при проверке синтаксиса. Посмотрим на фрагмент процедуры, где разработчик попытался перенести элементы справочника в другую группу:
&НаСервереБезКонтекста
Процедура ПеренестиВПредопределеннуюГруппуНаСервере()
КудаПеренести = Справочники.Номенклатура.ПрочиеТовары;
Выборка = Справочники.Номенклатура.Выбрать();
Пока Выборка.Следующий() Цикл
Если Не Выборка.Ссылка = КудаПеренести Тогда
ПолученныйОбъект = Выборка.ПолучитьОбъект();
ПолученныйОбъект.Родитель = КудаПеренести;
ПолученныйОбъект.Записать();
КонецЕсли;
КонецЦикла
КонецФункции
КонецПроцедуры
Выясним причину проблемы в данном коде. Обратим внимание на самый конец фрагмента: после закрытия цикла КонецЦикла мы видим подряд идущие КонецФункции и КонецПроцедуры. Программа была объявлена с помощью ключевого слова Процедура, однако внутри разработчик добавил лишнее ключевое слово КонецФункции. Парсер языка 1С строго следит за соответствием открывающих и закрывающих операторов. Встретив КонецФункции там, где его быть не должно, компилятор сбивается и выдает синтаксическую ошибку.
Разберем основные сценарии, при которых платформа 1С сообщает о том, что ожидается окончание процедуры или функции:
Процедура должна завершаться только через КонецПроцедуры. Любая Функция должна закрываться через КонецФункции. Перекрестное использование этих слов приведет к ошибке компиляции.Если ... Тогда или блок цикла Пока ... Цикл, но забыли написать КонецЕсли или КонецЦикла, парсер дойдет до конца модуля и не найдет логического завершения блока. В результате он укажет, что структура нарушена, и выдаст ошибку о том, что ожидается конец процедуры.Проанализируем еще один важный момент, связанный с логикой работы методов в 1С. Помимо правильного закрытия синтаксических блоков, необходимо помнить об операторе возврата значения.
Конструкция Функция всегда должна вычислять какой-либо результат и возвращать его в вызывающий код с помощью оператора Возврат Значение;. В то же время Процедура выполняет действие, но ничего не возвращает. В процедуре можно использовать оператор Возврат; (без передачи параметра), но только для досрочного прекращения выполнения алгоритма. Попытка вернуть значение из процедуры вызовет дополнительную синтаксическую ошибку.
Рассмотрим рабочие методы, которые помогут нам быстро локализовать проблему в больших модулях:
Если или Цикл не закрыт, весь последующий код сместится вправо. Место, где нарушается визуальная структура отступов, обычно и скрывает пропущенное или лишнее ключевое слово.&НаКлиенте или &НаСервере должны стоять строго перед объявлением метода. Между директивой и словом Процедура не должно быть лишнего кода или других процедур.Посмотрим на исправленный вариант кода, который успешно пройдет синтаксический контроль:
&НаСервереБезКонтекста
Процедура ПеренестиВПредопределеннуюГруппуНаСервере()
КудаПеренести = Справочники.Номенклатура.ПрочиеТовары;
Выборка = Справочники.Номенклатура.Выбрать();
Пока Выборка.Следующий() Цикл
Если Выборка.Ссылка <> КудаПеренести Тогда
ПолученныйОбъект = Выборка.ПолучитьОбъект();
ПолученныйОбъект.Родитель = КудаПеренести;
ПолученныйОбъект.Записать();
КонецЕсли;
КонецЦикла;
КонецПроцедуры
В исправленном варианте мы удалили лишнее слово КонецФункции и заменили конструкцию Не Выборка.Ссылка = КудаПеренести на более корректную и читаемую Выборка.Ссылка <> КудаПеренести. Применяя автоформатирование и внимательно следя за парными операторами, вы навсегда забудете о проблеме незакрытых процедур в 1С.