Я пытаюсь узнать, как работает приложение. И для этого я вставляю команды отладки в качестве первой строки тела каждой функции с целью регистрации имени функции, а также номера строки (в коде), куда я отправляю сообщение в вывод журнала. Наконец, поскольку это приложение состоит из множества файлов, я хочу создать один файл журнала, чтобы лучше понимать поток управления приложения.
Вот что я знаю:
для получения имени функции я могу использовать,
function_name.__name__
но не хочу использовать имя_функции (чтобы я мог быстро скопировать и вставить универсальный шаблонLog.info("Message")
в тело всех функций). Я знаю, что это можно сделать на C с помощью__func__
макроса, но я не уверен в питоне.для получения имени файла и номера строки я видел (и считаю, что) мое приложение использует
locals()
функцию Python, но в синтаксисе, о котором я не полностью осведомлен, например:options = "LOG.debug('%(flag)s : %(flag_get)s' % locals())
и я пробовал использовать like,LOG.info("My message %s" % locals())
который дает что-то вроде{'self': <__main__.Class_name object at 0x22f8cd0>}
. Любые комментарии по этому поводу, пожалуйста?Я знаю, как использовать ведение журнала и добавить к нему обработчик для записи в файл, но я не уверен, можно ли использовать один файл для записи всех сообщений журнала в правильном порядке вызовов функций в проекте.
Буду очень признателен за любую помощь.
Спасибо!
import pdb; pdb.set_trace()
, а затем выполнить код в интерактивном режиме. Это может помочь вам отслеживать выполнение программы.Ответы:
У вас есть несколько второстепенных вопросов.
Начну с самого простого: (3). С
logging
его помощью вы можете объединить все вызовы в один файл журнала или другую цель вывода: они будут в том порядке, в котором они произошли в процессе.Далее: (2).
locals()
предоставляет информацию о текущей области. Таким образом, в методе, не имеющем других аргументов, у вас естьself
область, которая содержит ссылку на текущий экземпляр. Используемый трюк, который ставит вас в тупик, - это форматирование строки с использованием dict в качестве правой части%
оператора."%(foo)s" % bar
будет заменен на любое значениеbar["foo"]
.Наконец, вы можете использовать некоторые уловки самоанализа, аналогичные тем, которые используются для
pdb
регистрации дополнительной информации:Это будет регистрировать переданное сообщение плюс (исходное) имя функции, имя файла, в котором появляется определение, и строку в этом файле. Взгляните на inspect - Осмотрите живые объекты для получения более подробной информации.
Как я уже упоминал в своем комментарии ранее, вы также можете перейти в
pdb
интерактивное приглашение отладки в любое время, вставив строкуimport pdb; pdb.set_trace()
и повторно запустив свою программу. Это позволяет вам выполнять код, проверяя данные по своему усмотрению.источник
'%(foo)s : %(bar)s'
также печататься значениеbar["foo"]
's? Или это несколько отличается от вашего примера?%(<foo>)s
заменяются значением объекта, на который ссылается dict by<foo>
. Больше примеров / подробностей можно найтиПравильный ответ - использовать уже предоставленную
funcName
переменнуюТогда куда угодно, просто добавьте:
Пример вывода сценария, над которым я сейчас работаю:
источник
getLogger(__name__)
logging.getLogger('root')
это не то, что вы ожидаете, это неroot
регистратор, а обычный регистратор с именем root.funcname
,linename
Иlineno
предоставить информацию о последней функции , что сделали вырубку.Если у вас есть оболочка регистратора (например, одноэлементный регистратор), то ответ @ synthesizerpatel может не сработать для вас.
Чтобы узнать других абонентов в стеке вызовов, вы можете:
источник
logging
класс поддерживает пропуск на уровне стека «из коробки»: такие методы, какlog()
,debug()
и т. Д., Теперь принимаютstacklevel
аргумент. См. Документы .