Причем в режиме выполнения и не исполняя собственно процедуру/функцию..?
Попытка/Исключение?
ЗЫ: А, не исполняя жеш...
1С++ ;)
Информатор.МетодСуществует(Контекст, "ПриОткрытии")
Но работает только для процедур/функций непосредственно из контекста.
Как получить контекст глобальника, я не знаю. И как получить экспортные методы, тоже не знаю.
Проверить в каком-то конкретном модуле надо?
Можно попробовать через 1С++::ВыполняемыйМодуль. Скормить текст модуля с вызовом нужной процедуры. Если не скомпилится, то нет такой.
Цитата: АЛьФ от 04 февраля 2025, 15:43Можно попробовать через 1С++::ВыполняемыйМодуль.
Но надо же будет соблюдать число параметров, или нет?
Цитата: Arbuz от 04 февраля 2025, 16:21Цитата: АЛьФ от 04 февраля 2025, 15:43Можно попробовать через 1С++::ВыполняемыйМодуль.
Но надо же будет соблюдать число параметров, или нет?
Надо будет. Поэтому ждем полную постановку задачи.
Вот:
Функция МетодСуществует(пМетод, пКонтекст = "")
_модуль = СоздатьОбъект("ВыполняемыйМодуль");
_модуль.УстановитьМодуль("
|Функция __Тест()
| " + пМетод + "()
|КонецФункции"
);
_модуль.НазначитьКонтекст(пКонтекст);
Попытка
_модуль.КомпилироватьИВыполнитьМодуль();
Возврат 1;
Исключение
Если Найти(ОписаниеОшибки(), "Недостаточно фактических параметров") > 0 Тогда
Возврат 1;
Иначе
Возврат 0;
КонецЕсли;
КонецПопытки;
КонецФункции
Если не передавать контекст, то проверяет только на экспортные методы глобальника.
Как проверять глобальник на приватные — ума не приложу, т.к. контекст глобальника это что-то очень специфическое.
ЗЫ: Проверять типа так Сообщить(МетодСуществует("ПриОткрытии", Контекст));
Через попытка исключение не пойдет ибо если процедуры нет, то обрушится на синтаксическом контроле при открытии модуля выполнения.
Можно сузить, считая что интересуют только экспортные процедуры/функции ГМ.
Цитата: Злоп от 04 февраля 2025, 22:57Через попытка исключение не пойдет ибо если процедуры нет, то обрушится на синтаксическом контроле при открытии модуля выполнения.
Расшифруй задачу
Ну, например, пишу универсальную обработку, на форме - ТЗ.
На ней кнопка "Печать". Да, можно вкорябать по быстрому простенькую печать ТЗ.
Но, обычно, во многих конфигах есть функция/процедура типа глПечатьТЗ, поэтому
хочется типа
Если ЕстьПроцедура(ИмяПроцедурыФункции)=1 Тогда
ВыполнитьПроцедуру(ИмяПроцедуры);
.
чтобы не ругалось на синтаксис если где-то впрямую пишем имя процедуры/функции, которой сожет и не быть в ГМ - можно, наверное, через Шаблон как-то проверять.
.
А вообще может это все хрень, что я извращаюсь
И ну его нафиг эти клюшки.
И снеговик туда же.
Так никогда нельзя быть уверенным, что глПечатьТЗ конкретно в этой конфе делает именно то, что тебе нужно. Может она рисует "главную печать" фирмы на переданном в функцию "техзадании" и делает e-mail рассылку готового ТЗ по всем подрядчикам.
Так что - всё своё приходится носить с собой, раз уж обработка универсальная...
Тогда надо делать обработку-контейнер с функциями/процедурами и макетами. Типа БСП.
Интересный факт, Информатор умеет работать не только с Объектами, но и с Контекстом.
ТЗ = Информатор.ПолучитьТаблицуМетодов(Контекст)
Так можно проверить наличие метода в текущем контексте, но не в конфигурации.
Цитата: Пиит от 06 февраля 2025, 11:15Интересный факт, Информатор умеет работать не только с Объектами, но и с Контекстом...
Сори, за баян, друзья.
Цитата: Пиит от 06 февраля 2025, 11:15Интересный факт, Информатор умеет работать не только с Объектами, но и с Контекстом.
ТЗ = Информатор.ПолучитьТаблицуМетодов(Контекст)
Так можно проверить наличие метода в текущем контексте, но не в конфигурации.
Экспортные методы глобального модуля туда не попадут.
А так, я же в #6 (https://forum.dorex.pro/index.php?msg=2918) уже сделал по наводке АЛьФ'а через проверку компиляции выполняемого модуля.
Чтобы "не ругалось на синтаксис" — чуть модифицировав туда можно добавить и выполнение в нужном контексте, но надо будет и параметры добавлять, например через сз.
Чтобы не ругалось на синтаксис - там какой-то хитрый кунштюк с подавлением вывода в окно сообщений вроде?
Вот, на тебе, специально с goto:
//======================================================================
// пМетод - Строка типа "глФРМ", "глФРМ()", "глФРМ(П1)", "глФРМ(П1,П2)"
// пКонтекст - Контекст выполнения, если пустой, то проверяется только экспорт ГМ
// впМодуль - возвращаемый объект типа 'ВыполняемыйМодуль' в котором есть процедура/функция "__Выполнить" для пМетод
// Возвращает: 0 - нет такого метода
// 1 - есть метод и доступен Выполняемый модуль в впМодуль
// -1 - метод есть, но недостаточно аргументов.
Функция МетодСуществует(Знач пМетод, пКонтекст = "", впМодуль = 0)
_Функция = 1;
_ПозПараметров = Найти(пМетод, "(");
Если _ПозПараметров = 0 Тогда
_Параметры = "()";
пМетод = пМетод + _Параметры;
Иначе
_Параметры = Сред(пМетод, _ПозПараметров);
КонецЕсли;
~Метка:
Если ТипЗначенияСтр(впМодуль) <> "ВыполняемыйМодуль" Тогда
впМодуль = СоздатьОбъект("ВыполняемыйМодуль");
КонецЕсли;
впМодуль.УстановитьМодуль("
|" + ?(_Функция = 1, "Функция", "Процедура") + " __Выполнить" + _Параметры + "
| " + ?(_Функция = 1, "Возврат ", "") + пМетод + "
|" + ?(_Функция = 1, "КонецФункции", "КонецПроцедуры") + "
);
впМодуль.НазначитьКонтекст(пКонтекст);
Попытка
//Сообщить(впМодуль.ПолучитьТекстМодуля());
впМодуль.КомпилироватьИВыполнитьМодуль();
//Сообщить("Ошибок нет");
Возврат 1;
Исключение
//Сообщить(ОписаниеОшибки());
Если Найти(ОписаниеОшибки(), "Процедура вызывается как функция") > 0 Тогда
_Функция = 0;
Перейти ~Метка;
ИначеЕсли (0=1)
ИЛИ (Найти(ОписаниеОшибки(), "Недостаточно фактических параметров") > 0)
ИЛИ (Найти(ОписаниеОшибки(), "TODO: ДОБАВИТЬ УСЛОВИЙ") > 0) // !!! TODO: ДОБАВИТЬ УСЛОВИЙ
Тогда
Возврат -1;
Иначе
Возврат 0;
КонецЕсли;
КонецПопытки;
КонецФункции // МетодСуществует
Использовать как-то так:
Сообщить(МетодСуществует("__Выполнить", Контекст));
Сообщить(МетодСуществует("глФРМ"));
Сообщить(МетодСуществует("глФРМ()"));
Сообщить(МетодСуществует("глФРМ(П1)"));
Сообщить(МетодСуществует("глФРМ(П1,П2)"));
Сообщить(МетодСуществует("ПриОткрытии", КакойтоКонтекст, _вм));
_вм.__Выполнить();
Сообщить(МетодСуществует("глОтладка"));
Если МетодСуществует("глОтладка(П1,П2,П3)", Контекст, _вм) = 1 Тогда
_вм.__Выполнить("123",1,0);
КонецЕсли;
Надо будет проверить...