При сопровождении и доработке типовых конфигураций 1С на обычных формах (например, УТП, УПП, КА 1.1) разработчики иногда сталкиваются с неожиданной ситуацией: при попытке вызвать экспортную функцию из модуля менеджера объекта возникает ошибка «Метод объекта не обнаружен», хотя сама функция присутствует в конфигурации и объявлена со словом Экспорт.
Проанализируем типовую ситуацию, выясним технические причины такого поведения платформы 1С и разберем по шагам несколько способов надежного устранения проблемы.
Рассмотрим пример кода, с которым возникает ошибка при обращении из модуля объекта или формы справочника:
СписокТНВЭДПереченьИзъятий = РегистрыСведений.ТоварыСПониженнойСтавкойПошлин.ЗаполнитьСписокПереченьИзъятий();
При выполнении этой строки в режиме «Толстый клиент (обычное приложение)» платформа генерирует исключение: {Справочник.Номенклатура.МодульОбъекта(97)}: Метод объекта не обнаружен (ЗаполнитьСписокПереченьИзъятий).
Заглянем в модуль менеджера регистра сведений ТоварыСПониженнойСтавкойПошлин и посмотрим на объявление метода:
#Если Сервер Или ТолстыйКлиентОбычноеПриложение Или ВнешнееСоединение Тогда
&НаСервере
Функция ЗаполнитьСписокПереченьИзъятий() Экспорт
СписокТНВЭДПереченьИзъятий = Новый СписокЗначений;
ПереченьИзъятий = ПолучитьАктуальныйПереченьИзъятий();
СписокТНВЭДПереченьИзъятий.ЗагрузитьЗначения(ПереченьИзъятий);
Возврат СписокТНВЭДПереченьИзъятий;
КонецФункции
#КонецЕсли
Выясним причину такого поведения. Здесь действуют два ключевых фактора:
&НаСервере, &НаКлиенте и &НаСервереБезКонтекста предназначены исключительно для модулей управляемых форм и команд. В модулях менеджеров, модулях объектов и общих модулях контекст исполнения задается только свойствами модуля и инструкциями препроцессора (#Если ... Тогда). Наличие строки &НаСервере в модуле менеджера является следствием некорректного копирования кода разработчиками типовых решений из управляемых форм. Платформа при разборе модуля с такой директивой исключает функцию из таблицы доступных экспортных методов.Если проблемный объект находится на замке поставщика и менять правила поддержки нежелательно, используем универсальный обходной путь — создадим отдельный общий модуль-посредник.
Разберем реализацию по шагам:
ИнтеграцияСерверВызовСервера).
Функция ЗаполнитьСписокПереченьИзъятий() Экспорт
Возврат РегистрыСведений.ТоварыСПониженнойСтавкойПошлин.ЗаполнитьСписокПереченьИзъятий();
КонецФункции
СписокТНВЭДПереченьИзъятий = ИнтеграцияСерверВызовСервера.ЗаполнитьСписокПереченьИзъятий();
Благодаря флагу Вызов сервера клиентское приложение безопасно переходит в серверный контекст, где метод менеджера выполняется без ошибок.
Если конфигурация уже снята с полной поддержки и допускает внесение правок в объекты поставщика, наиболее правильным с точки зрения синтаксиса решением будет удаление ошибочной директивы.
Посмотрим на исправленный фрагмент модуля менеджера:
#Если Сервер Или ТолстыйКлиентОбычноеПриложение Или ВнешнееСоединение Тогда
Функция ЗаполнитьСписокПереченьИзъятий() Экспорт
СписокТНВЭДПереченьИзъятий = Новый СписокЗначений;
ПереченьИзъятий = ПолучитьАктуальныйПереченьИзъятий();
СписокТНВЭДПереченьИзъятий.ЗагрузитьЗначения(ПереченьИзъятий);
Возврат СписокТНВЭДПереченьИзъятий;
КонецФункции
#КонецЕсли
Мы удалили строку &НаСервере, оставив только корректные инструкции препроцессора. После этого метод станет полноценно доступен и на сервере, и в обычном толстом клиенте.
Если основную конфигурацию категорически запрещено снимать с поддержки (даже частично), применим механизм расширений платформы 1С:Предприятие 8.3:
Такой подход сохраняет типовую конфигурацию на полной поддержке поставщика и гарантирует беспрепятственное накатывание будущих релизов обновлений.