|
Узнать откуда вызвана функция без "Сообщить()" | ☑ | ||
---|---|---|---|---|
0
timeforlive
25.01.15
✎
17:25
|
Всем привет!
Есть ли метод, позволяющий узнать откуда вызвана функция в режиме отладки (строка в коде, откуда вызвана функция)? Назовем ее функция "А", чтобы не путаться. Объясню подробнее: 1. не используется метод Попытка-Исключение-КонецПопытки Так как в функции "А" предусмотрены все исключения и соответственно имеется возвращаемое значение на этот случай. Следователь, метод ОписаниеОшибки() отпадает; 2. не использовать метод Сообщить() Так как функция "А" используется в модуле в разных местах (процедурах и других функциях), а также в саму функцию "А" нет смысла вставлять метод Сообщить() - ведь пользователю не нужна лишняя техническая информация. 3. не использовать точки останова Так как функция "А" используется в разных местах, то каждый раз ее обрабатывать (даже через F5) будет долго. 4. не использовать вариант "Изменения кода на лету" То есть, об этом говорится в теме по ссылке ниже, но мне нужно не менять код, а знать откуда вызвана функция. Ссылка: Книга знаний: Хитрости отладки 5. не использовать "обозримую трассировку" С той же ссылки. Слишком долго будет каждый раз переводить в комментарии (и обратно в исполняемый код) метод с точкой запятой - ;Сообщить() В Конфигураторе есть возможность узнать, где именно исполняется код в настоящий момент: Отладка -> Стек вызовов Достаточная информация, но даже, если создать исключение (с возвращаемым значением), будет не известно, откуда была вызвана функция. Что подскажите? Может есть нужный мне метод, чтобы не изобретать велосипед. |
|||
1
Asmody
25.01.15
✎
17:37
|
Подобное желание говорит об ошибках проектирования
|
|||
2
GROOVY
25.01.15
✎
17:42
|
Стек вызовов это называется. Одной кнопкой в конфигураторе делается.
|
|||
3
Asmody
25.01.15
✎
17:44
|
(2) т.е., ты признаёшь, что полностью вопрос не прочитал?
|
|||
4
Escander
25.01.15
✎
17:45
|
(0) >В Конфигураторе есть возможность узнать, где именно исполняется код в настоящий момент:
Отладка -> Стек вызовов Достаточная информация, но даже, если создать исключение (с возвращаемым значением), будет не известно, откуда была вызвана функция. вы что-то переработали что-ли? В Стеке есть полный список кто откуда кого вызывал, даже если там был код модулей без исходников (рарус такие часто втыкает в конфигцурации). |
|||
5
Escander
25.01.15
✎
17:47
|
(3) там поток усталого сознанья
|
|||
6
Asmody
25.01.15
✎
17:51
|
(4) если я правильно понял, у ТС функция вызывается из 100500 разных мест. И в каком-то из этих мест она глючит. Он ее хочет остановить именно тогда, когда она была вызвана из того места.
|
|||
7
Defender aka LINN
25.01.15
✎
17:55
|
"Так как функция "А" используется в разных местах, то каждый раз ее обрабатывать (даже через F5) будет долго." - вы знаете, в нашей работе иногда приходится таки работать...
|
|||
8
Escander
25.01.15
✎
17:56
|
(6) 1.если там происходит ошибка: включить останов по ошибке и смотреть стек,
2.если нет ошибки но есть к примеру некое значение в какой-то переменной которое явно говорит о том что всё плохо - точка останова с условием + стек вызова... не устраивает его вывод тех. информации через Сообщить - пусть пишет при каждом вызове всё что ему нужно в текстовый файл а потом парсит его и по варианту 2. ну или я вообще не понял что он хочет. |
|||
9
GROOVY
25.01.15
✎
17:57
|
(3) Я должен отчитываться?
Из стеков вызова с нормальными руками и мозгами можно вполне себе найти точку входа. |
|||
10
Serg_1960
25.01.15
✎
18:00
|
Хмм... из "усталого потока сознания" :), я так понял, что ТС хочет программно определить откуда вызов :)
|
|||
11
Escander
25.01.15
✎
18:01
|
(10) а ключ от квартиры где деньги лежат ему не надо?
|
|||
12
ShoGUN
25.01.15
✎
18:03
|
(8) +1. Поставить точку останова с условием, и смотреть стек вызовов.
|
|||
13
timeforlive
26.01.15
✎
05:19
|
Спасибо за ответы.
Придется озарить тьму, которая не видна в моем вопросе (сарказм). 1. Мест откуда вызывается функция - множество (100500 мест). 2. Функция предусматривает все исключения и возвращает "Значение", на этот счет, пример в студию: Функция МояФункция(параметр1, параметр2-Истина, параметр3-Ложь, параметр4-исключение) параметр2 и параметр3 на случай проверки в функции определенных алгоритмов одному из утверждению (булево). параметр-4 на случай исключения (самый распрастраненный пример - деление на ноль). Иногда нужно возвращать значение даже при наличии исключения, вот так. 3. Именно программно нужно определять откуда вызвана функция. По сути, в методе ОписаниеОшибки() имеется ифнформация в какой строке кода случилась ошибка. Я подумал, что есть и отдельный метод, который определяет свое место в коде по строке. Тогда пример функции был бы такой: Функция МояФункция (параметр1, параметр2, параметр3, параметр4, СтрокКода), где СтрокаКода - это и есть определение места вызова функции, а в момент срабатывания моего "исключения" можно (хотя бы) через Сообщить("ошибка функции" + "<название функции>: " + "место вызова функции: " + СтрокаКода) |
|||
14
timeforlive
26.01.15
✎
05:21
|
"озарить тьму на мой вопрос"*
:) |
|||
15
kosts
26.01.15
✎
06:29
|
(13) Условная точка остановки, остановка по исключению, что еще надо.
|
|||
16
VladZ
26.01.15
✎
06:44
|
(0) Обычно такой функционал никому не нужен. Задача функции - выполнить определенный кусок кода. Кому и для чего - эта уже определяется в другом контексте.
В чем у тебя проблема? Отладить не можешь? Что-то ломает твою "стройную" систему, а ты не можешь поймать что это? |
|||
17
VladZ
26.01.15
✎
06:45
|
Пиши логи. И анализируй.
|
|||
18
DrZombi
гуру
26.01.15
✎
07:42
|
Много буковок, но :
1. Если это Рабочий сервер, сделай себе копию БД, либо парси код. :) 2. В копии пропиши "-debug", в реестре через RegEdit в строке запуска службы Сервера приложений 1С :) |
|||
19
DrZombi
гуру
26.01.15
✎
07:43
|
(16) Скорей всего ему вломы потратить 10 минут :)
|
|||
20
IUnknown
26.01.15
✎
07:47
|
(19)а может просто тупо не знает
|
|||
21
timeforlive
26.01.15
✎
07:58
|
Все работает у меня. Была проблема - просто через метод Сообщить() и точки останова выявлял и устранял ошибку.
Иногда люблю заниматься рефакторингом, мой минус... от чего выявляются другие ошибки, оптимизирую функцию, делаю ее более универсальной, чтобы пользоваться самому в будущем и другим разработчикам в команде. Ладно, думал, что есть метод, определяющий свое расположение в коде (в строке кода). Тема закрыта. |
|||
22
ADirks
26.01.15
✎
07:58
|
А если искуственно вызвать исключение? Типа
Если КакаяТоФигня Тогда Попытка а = 1 / 0; Исключение Сообщить(ОписаниеОшибки()); КонецПопытки; КонецЕсли; |
|||
23
Помогите
26.01.15
✎
08:03
|
Все гораздо проще.
Если КакаяТоФигня Тогда a=0; // Поставь в этой строке точку остановки, и через стек вызовов узнаешь откуда была вызвана функция. КонецЕсли; |
|||
24
timeforlive
26.01.15
✎
09:24
|
(22) у вас ОписаниеОшибки укажет строку в функции.
Все предусмотренные мною исключения возвращают значение, которое предусмотрено параметром4. (23) если делать точку останова, то опять же, мы будет работать с функцией. Вот вам пример на пальцах (моя функция, конечно, другая, но механизм похож): [code] Процедура Если МояФункция(1, 0, ЛОЖЬ) Тогда Х = МояФункция(1, 0, 1); КонецЕсли КонецПроцедуры Функция МояФункция (параметр1Число, параметр2Число, параметр3Исключение) // проверка на тип Если НЕ ТипЗнч(параметр2Число) = Тип("Число") Тогда Возврат параметр3Исключение; КонецЕсли; // проверка на "деление на ноль" Если параметр2Число = 0 Тогда Возврат параметр3Исключение; КонецЕсли; // выполняем функцию, если нет исключений Возврат параметр1Число \ Параметр2Число; КонецФункции; [/code] P.S. не нашел визуальную панель для редактирования текста с использованием BBcode |
|||
25
timeforlive
26.01.15
✎
09:26
|
Если МояФункция(1, 0, ЛОЖЬ) Тогда
Х = МояФункция(1, 0, 1); КонецЕсли третий параметр, конечно, никогда не будет срабатывать, при условии ИСТИНА при проверке. |
|||
26
kosts
26.01.15
✎
09:28
|
(24) Проблема, о в чем?
|
|||
27
Salimbek
26.01.15
✎
09:33
|
(26) Я так понимаю, что в конце длиннющего кода у него есть "Результат = 8" и он хочет понять - когда именно у него получилось "8".
(24) Варианты: 1. Как было правильно сказано - точка останова с условием "Результат = 8" и смотришь - в каком именно месте получилось такое. 2. В функцию вставляем запись в лог-файл входных параметров + добавляем дополнительный контекстный параметр (например для Табличной части - можно добавить Номенклатуру, чтобы понять на каком именно товаре был произведен данный расчет) |
|||
28
VladZ
26.01.15
✎
09:47
|
(25) а у тебя результат "Истина" и не возвращается. Либо "ложь", либо результат деления. Что ты проверяешь в этом условии - непонятно.
В целом, код в (24) - несвязный поток сознания. |
|||
29
Лефмихалыч
26.01.15
✎
09:52
|
я бы за одно вот это (0) выпилил к херам свинячьим на уровне базы данных все статьи сосипана из КЗ. Чтобы новообращенным не пудрились мозги ересью
|
|||
30
Лефмихалыч
26.01.15
✎
09:55
|
есть такая штука в отладчике "Останавливаться по ошибке", она призвана помогать останавливать там, где падает в случаях, когда вызывается из 100500 мест и хрен пойми, что ей надо
|
|||
31
Asmody
26.01.15
✎
09:57
|
(21) Как-то вы неправильно рефакторите. Если функция хочет знать откуда она вызвана, значит в функции что-то не так.
|
|||
32
Лефмихалыч
26.01.15
✎
10:00
|
(31) +1 это называется не "рефакторинг", а "доломал"
|
|||
33
art-adm
26.01.15
✎
10:11
|
Если правильно понял : дополнить функцию дополнительным параметром с типом значение "число". И по этому параметру уже узнавать откуда была вызвана функция. Например, если из внешней обработки отправляешь в параметр "0", если из определенного документа - "1" и.т.д. Если функция вызывает исключение отправляешь данные вместе с этим параметром в лог-текст + время. По этому числу и выяснишь откуда произошел вызов функции до вызванного исключения. Но если вызывается из +100500 мест, менять придется много.
|
|||
34
VladZ
26.01.15
✎
10:15
|
(32) Это называется "рефакинг".
|
|||
35
Asmody
26.01.15
✎
10:25
|
(33) в 1С есть значения параметров по-умолчанию.
|
|||
36
timeforlive
26.01.15
✎
12:21
|
Нервные вы все какие-то...
(30) - то же самое что Попытка-Исключение, ошибки не будет, если я предусмотрел все исключения в функции. (32), (34) - "роза пахнет розой, как ее не назови", верно? (33) - что-то ближе к истине, не понял только про время: "лог-текст + время". Натолкнули на мысль, чтобы создать новый параметр не Число, а Строка, в которую можно будет поместить (ну на крайний случай) имя переменной, которой будет присваиваться значение. Так количество мест с ошибкой будет снижен. Допустим, можно будет в Табло внести эту переменную и отследить в какой момент она принимает не правильное значение, вот. Менять эту функцию не стану, сейчас она отлажена как надо, но в будущем метод определения откуда вызвана функция мне понадобится. |
|||
37
art-adm
26.01.15
✎
21:57
|
(36) "Лог-текст+время" - записывать данные в обычный текстовый документ. Если заморочиться на скорости выполнения - можно сделать для лога отдельный регистр сведений, и все данные до исключения: доп.параметр, который обозначит место вызова , переменная с неправильным значением, время и.т.д. писать туда.
|
|||
38
Dionis Sergeevich
26.01.15
✎
22:31
|
все не читал. Если это нужно на этапе разработки (если функция вызвана от туда то то делаем то-то иначе то-то) то просто добавляем необязательный параметр. А вообще в топике нужно было обозначить цели а не способы достижения - много бы хороших вариантов нашлось ИМХО
|
|||
39
Dionis Sergeevich
26.01.15
✎
22:33
|
НАпример Функция(,,,,Объект.Метаданные());
Даже методами объекта позволит пользоваться. Но это только сервер-сервер. |
|||
40
Dionis Sergeevich
26.01.15
✎
22:40
|
И вообще это какое-то зло неоптимальное...
|
|||
41
orefkov
26.01.15
✎
22:59
|
(0)
Функции в языках программирования и были придуманы, чтобы не зависеть от вызывающего контекста. Поведение функции должно полностью определятся переданными параметрами. Если у вас в функции возникла необходимость разного поведения в зависимости от того, откуда она была вызвана, это говорит об ошибке проектирования - думайте над параметрами функции. |
|||
42
VladZ
27.01.15
✎
06:22
|
(37) Обычно хватает и текста. Я бы не стал "пихать" логи в рабочую базу данных. Слишком быстро "засирается" ненужной инфой. Для повышения быстродействия можно засунуть лог в какую-нибудь внешнюю базу данных.
|
|||
43
фобец
27.01.15
✎
08:37
|
(13) передай в качестве параметра номер или какойто ид строки и имя модуля из которой вызывал метод. Ну и так в 100500 местах
|
|||
44
artbear
27.01.15
✎
14:38
|
(0) При разработке фреймворка автоматизированного тестирования xUnitFor1C мне в свое время также пришлось столкнуться с подобной проблемой.
Решил, как уже предлагалось выше: есть последний спец.параметр, в котором передается некая строка с описанием проблемы или вызывающего кода. значение по умолчанию пустая строка. формат строки неопределен. Желательно обеспечить уникальность этого параметра для возможности поиска по коду. ИМХО ничего другого пока 1С предложить не может :( |
|||
45
timeforlive
28.01.15
✎
07:11
|
(44) Спасибо.
Думаю, так и делать покамест для сложных, "многоюзабельных" функций. Определение места вызова функции также схож, как определение наименования самой функции \ переменной (т.е. нет метода, который бы определял имя переменной, если разработчик явно не запихнет это в виде Строки), хотя последнее мне нигде не пригождалось. Кстати, пришла идея. Может вместо определения места вызова функции определять какие параметры в нее были переданы (хоть и не хочется открывать "тайны" пользователю, но можно всегда значение "параметров" и наименование (или ссылку на объект) "параметра" зашифровать простым способом, это если совсем хочется усложнить себе работу). |
|||
46
SUA
28.01.15
✎
18:04
|
а кому-то потом такую нетленку разгребать...
правильный ответ в (32) и как пользователю, так и программисту должно быть глубоко параллельно, откуда вызвана функция, если программа в этой функции не лажает |
|||
47
timeforlive
29.01.15
✎
15:36
|
Конечно, писать красивый и 100%-работающий код все хотят, но не всегда получается.
Если программа будет работать исправно, то ни пользователь, ни разработчик не будет информирован о том, где вызывается функция, т.к. она не будет выдавать такого сообщения в принципе. Но если уж случись проблема (а особенно на альфа-версиях обработки), то время - это все, что есть у разработчика, чтобы вовремя устранить проблему. |
|||
48
Помогите
04.02.15
✎
08:08
|
Так чем тебя (23) не устраивает?
В твоем случае: Если НЕ ТипЗнч(параметр2Число) = Тип("Число") Тогда Возврат параметр3Исключение; // Тут ставь точку останова КонецЕсли; и узнаешь откуда вызвана функция через стек вызовов. |
|||
49
artbear
11.02.15
✎
12:06
|
Присоединюсь к (41)
Как правило, функции не нужно знать, откуда она вызвана. Только в исключительных, редких случаях это нужно. |
|||
50
timeforlive
17.02.15
✎
05:03
|
Я думаю, если ожидается, что функцию придется "допиливать" и ожидается знать откуда она вызывается, то можно будет создать параметр типа число, куда заносить порядковый номер (либо Строку, как удобно), например, "ОткудаВызванаФункция".
Такой параметр можно будет заполнить нулем, если он не нужен.. ну как-то так. |
|||
51
Domovoi
19.02.15
✎
13:56
|
Всегда удивлялся людям, которые программят абы как, а потом делают многовековые проверки. Почему не пойти простым путем: начать стараться программить без ошибок?
|
Форум | Правила | Описание | Объявления | Секции | Поиск | Книга знаний | Вики-миста |