Spec-Zone.ru › Python 3.12

pdb — отладчик Python

Исходный код: Lib/pdb.py

Модуль pdb определяет интерактивный отладчик исходного кода для программ Python. Он поддерживает установку точек останова (в том числе условных) и пошаговое выполнение на уровне строк исходного кода, просмотр кадров стека, вывод исходного кода и вычисление произвольного кода Python в контексте любого кадра стека. Он также поддерживает посмертную отладку и может вызываться из программы.

Отладчик можно расширять — фактически он определён как класс Pdb. В настоящее время это не документировано, но разобраться в устройстве класса несложно, прочитав исходный код. Интерфейс расширения использует модули bdb и cmd.

См. также

Module faulthandler

Используется для явного вывода трассировок Python при сбое, по истечении времени ожидания или при получении пользовательского сигнала.

Module traceback

Стандартный интерфейс для извлечения, форматирования и вывода трассировок стека программ Python.

Обычно для перехода в режим отладки вставляют:

import pdb; pdb.set_trace()

Или:

breakpoint()

в место, где нужно перейти в режим отладки, а затем запускают программу. После этого можно пошагово выполнять код, следующий за этой инструкцией, и продолжить выполнение без отладчика с помощью команды continue.

Изменено в версии 3.7: Встроенную функцию breakpoint() при вызове без аргументов можно использовать вместо import pdb; pdb.set_trace().

def double(x):
   breakpoint()
   return x * 2
val = 3
print(f"{val} * 2 is {double(val)}")

Приглашение отладчика — (Pdb), оно показывает, что вы находитесь в режиме отладки:

> ...(3)double()
-> return x * 2
(Pdb) p x
3
(Pdb) continue
3 * 2 is 6

Изменено в версии 3.3: Для команд и их аргументов доступно автодополнение по клавише Tab с помощью модуля readline; например, текущие глобальные и локальные имена предлагаются в качестве аргументов команды p.

Вы также можете вызвать pdb из командной строки для отладки других скриптов. Например:

python -m pdb myscript.py

При вызове в качестве модуля pdb автоматически переходит к посмертной отладке, если выполнение отлаживаемой программы завершается аварийно. После посмертной отладки (или после нормального завершения программы) pdb перезапускает программу. Автоматический перезапуск сохраняет состояние pdb (например, точки останова) и в большинстве случаев полезнее, чем выход из отладчика после завершения программы.

Изменено в версии 3.2: Добавлен параметр -c для выполнения команд так, как если бы они были указаны в файле .pdbrc; см. раздел Команды отладчика.

Изменено в версии 3.7: Добавлен параметр -m для выполнения модулей так же, как это делает python -m. Как и при запуске скрипта, отладчик приостановит выполнение непосредственно перед первой строкой модуля.

Обычно для выполнения инструкции под управлением отладчика используют:

>>> import pdb
>>> def f(x):
...     print(1 / x)
>>> pdb.run("f(2)")
> <string>(1)<module>()
(Pdb) continue
0.5
>>>

Обычно для изучения аварийно завершившейся программы используют:

>>> import pdb
>>> def f(x):
...     print(1 / x)
...
>>> f(0)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 2, in f
ZeroDivisionError: division by zero
>>> pdb.pm()
> <stdin>(2)f()
(Pdb) p x
0
(Pdb)

Модуль определяет следующие функции; каждая из них немного по-разному запускает отладчик:

pdb.run(statement, globals=None, locals=None)

Выполнить инструкцию (заданную в виде строки или объекта кода) под управлением отладчика. Приглашение отладчика появляется до выполнения какого-либо кода; можно установить точки останова и ввести continue либо пошагово выполнить инструкцию с помощью step или next (все эти команды описаны ниже). Необязательные аргументы globals и locals задают среду, в которой выполняется код; по умолчанию используется словарь модуля __main__. (См. описание встроенных функций exec() или eval().)

pdb.runeval(expression, globals=None, locals=None)

Вычислить выражение (заданное в виде строки или объекта кода) под управлением отладчика. Функция runeval() возвращает значение выражения. В остальном эта функция аналогична run().

pdb.runcall(function, *args, **kwds)

Вызвать функцию (объект функции или метода, а не строку) с заданными аргументами. Когда функция runcall() возвращает управление, она возвращает результат вызова функции. Приглашение отладчика появляется сразу после входа в функцию.

pdb.set_trace(*, header=None)

Перейти в режим отладки в вызывающем кадре стека. Это полезно для установки жёстко заданной точки останова в определённом месте программы, даже если код в остальном не отлаживается (например, при сбое утверждения). Если указан аргумент header, он выводится в консоль непосредственно перед началом отладки.

Изменено в версии 3.7: Добавлен аргумент только по ключевому слову header.

pdb.post_mortem(traceback=None)

Перейти к посмертной отладке заданного объекта traceback. Если traceback не указан, используется трассировка исключения, которое обрабатывается в данный момент (для использования значения по умолчанию должно обрабатываться исключение).

pdb.pm()

Перейти к посмертной отладке трассировки, найденной в sys.last_traceback.

Функции run* и set_trace() являются псевдонимами для создания экземпляра класса Pdb и вызова метода с тем же именем. Чтобы получить доступ к дополнительным возможностям, нужно сделать это самостоятельно:

class pdb.Pdb(completekey='tab', stdin=None, stdout=None, skip=None, nosigint=False, readrc=True)

Pdb — это класс отладчика.

Аргументы completekey, stdin и stdout передаются базовому классу cmd.Cmd; см. его описание.

Аргумент skip, если он указан, должен быть итерируемым объектом с шаблонами имён модулей в стиле glob. Отладчик не будет переходить внутрь кадров, происходящих из модулей, имена которых соответствуют одному из этих шаблонов. [1]

По умолчанию Pdb устанавливает обработчик сигнала SIGINT (который отправляется, когда пользователь нажимает Ctrl-C в консоли) при получении команды continue. Это позволяет снова перейти в режим отладки, нажав Ctrl-C. Чтобы Pdb не изменял обработчик SIGINT, установите для nosigint значение true.

Аргумент readrc по умолчанию имеет значение true и определяет, будет ли Pdb загружать файлы .pdbrc из файловой системы.

Пример вызова для включения трассировки с аргументом skip:

import pdb; pdb.Pdb(skip=['django.*']).set_trace()

Вызывает событие аудита pdb.Pdb без аргументов.

Изменено в версии 3.1: Добавлен параметр skip.

Изменено в версии 3.2: Добавлен параметр nosigint. Ранее Pdb никогда не устанавливал обработчик SIGINT.

Изменено в версии 3.6: Добавлен аргумент readrc.

run(statement, globals=None, locals=None)
runeval(expression, globals=None, locals=None)
runcall(function, *args, **kwds)
set_trace()

См. документацию к описанным выше функциям.

Команды отладчика

Ниже перечислены команды, распознаваемые отладчиком. Большинство команд можно сокращать до одной или двух букв, как указано; например, h(elp) означает, что для ввода команды справки можно использовать h или help (но не he или hel, а также не H, Help или HELP). Аргументы команд должны отделяться пробелами или табуляцией. Необязательные аргументы в синтаксисе команд заключаются в квадратные скобки ([]); вводить квадратные скобки не нужно. Альтернативы в синтаксисе команд разделяются вертикальной чертой (|).

Пустая строка повторяет последнюю введённую команду. Исключение: если последней командой была команда list, выводятся следующие 11 строк.

Команды, которые отладчик не распознаёт, считаются инструкциями Python и выполняются в контексте отлаживаемой программы. Перед инструкциями Python также можно поставить восклицательный знак (!). Это эффективный способ изучить отлаживаемую программу; можно даже изменить переменную или вызвать функцию. Если при выполнении такой инструкции возникает исключение, выводится его имя, но состояние отладчика не меняется.

Отладчик поддерживает псевдонимы. У псевдонимов могут быть параметры, что позволяет в некоторой степени адаптировать их к исследуемому контексту.

В одной строке можно вводить несколько команд, разделяя их с помощью ;;. (Одиночный ; не используется, поскольку он служит разделителем команд в строке, передаваемой синтаксическому анализатору Python.) При разделении команд никакой дополнительный анализ не выполняется: ввод разбивается по первой паре ;;, даже если она находится внутри строки в кавычках. Для строк с двойными точками с запятой можно использовать неявную конкатенацию строк ';'';' или ";"";".

Чтобы задать временную глобальную переменную, используйте удобную переменную. Удобная переменная — это переменная, имя которой начинается с $. Например, $foo = 1 задаёт глобальную переменную $foo, которую можно использовать в сеансе отладчика. Удобные переменные очищаются при возобновлении выполнения программы, поэтому вероятность их влияния на программу меньше, чем при использовании обычных переменных, таких как foo = 1.

Предусмотрены три предварительно заданные удобные переменные:

  • $_frame: текущий отлаживаемый кадр
  • $_retval: возвращаемое значение, если кадр возвращает управление
  • $_exception: исключение, если кадр вызывает исключение

Добавлено в версии 3.12: Добавлена возможность использовать удобные переменные.

Если файл .pdbrc существует в домашнем каталоге пользователя или в текущем каталоге, он считывается с кодировкой 'utf-8' и выполняется так, как если бы его ввели в приглашении отладчика; пустые строки и строки, начинающиеся с #, игнорируются. Это особенно удобно для псевдонимов. Если существуют оба файла, сначала считывается файл из домашнего каталога, а определённые в нём псевдонимы можно переопределить в локальном файле.

Изменено в версии 3.2: Теперь .pdbrc может содержать команды, продолжающие отладку, например continue или next. Ранее эти команды не действовали.

Изменено в версии 3.11: Теперь .pdbrc считывается с кодировкой 'utf-8'. Ранее он считывался с кодировкой системной локали.

h(elp) [command]

Без аргументов выводит список доступных команд. Если аргументом является команда, выводит справку по этой команде. help pdb выводит полную документацию (строку документации модуля pdb). Поскольку аргумент команда должен быть идентификатором, для получения справки по команде ! необходимо ввести help exec.

w(here)

Выводит трассировку стека, помещая самый последний кадр внизу. Текущий кадр, определяющий контекст большинства команд, отмечается стрелкой (>).

d(own) [count]

Перемещает текущий кадр на count уровней (по умолчанию на один) вниз по трассировке стека (к более новому кадру).

u(p) [count]

Перемещает текущий кадр на count уровней (по умолчанию на один) вверх по трассировке стека (к более старому кадру).

b(reak) [([filename:]lineno | function) [, condition]]

Если указан аргумент lineno, устанавливает точку останова в этой строке текущего файла. Если указан аргумент function, устанавливает точку останова на первой исполняемой инструкции этой функции. Перед номером строки можно указать имя файла и двоеточие, чтобы задать точку останова в другом файле (возможно, ещё не загруженном). Файл ищется по путям из sys.path. Обратите внимание: каждой точке останова присваивается номер, на который ссылаются остальные команды для работы с точками останова.

Если присутствует второй аргумент, это выражение, которое должно вычислиться в истинное значение, чтобы сработала точка останова.

Без аргументов выводит все точки останова, а также для каждой из них — число срабатываний, текущий счётчик игнорирования и связанное условие, если оно есть.

tbreak [([filename:]lineno | function) [, condition]]

Временная точка останова, автоматически удаляемая при первом срабатывании. Аргументы те же, что и у команды break.

cl(ear) [filename:lineno | bpnumber ...]

Если указан аргумент filename:lineno, удаляет все точки останова в этой строке. Если указан разделённый пробелами список номеров точек останова, удаляет эти точки. Без аргументов удаляет все точки останова (предварительно запросив подтверждение).

disable bpnumber [bpnumber ...]

Отключает точки останова, указанные в разделённом пробелами списке номеров. Отключённая точка останова не может остановить выполнение программы, но, в отличие от удалённой точки останова, остаётся в списке и может быть включена снова.

enable bpnumber [bpnumber ...]

Включает указанные точки останова.

ignore bpnumber [count]

Задаёт счётчик игнорирования для точки останова с указанным номером. Если count не указан, счётчик игнорирования устанавливается в 0. Точка останова становится активной, когда счётчик игнорирования равен нулю. Если он ненулевой, значение count уменьшается при каждом достижении точки останова, если она не отключена и связанное с ней условие вычисляется в истинное значение.

condition bpnumber [condition]

Задаёт новое условие для точки останова — выражение, которое должно вычислиться в истинное значение, чтобы точка останова сработала. Если condition не указан, существующее условие удаляется; точка останова становится безусловной.

commands [bpnumber]

Задаёт список команд для точки останова с номером bpnumber. Сами команды вводятся в следующих строках. Чтобы завершить ввод команд, введите строку, содержащую только end. Пример:

(Pdb) commands 1
(com) p some_variable
(com) end
(Pdb)

Чтобы удалить все команды точки останова, введите commands, а сразу после неё — end; то есть не указывайте никаких команд.

Если аргумент bpnumber не указан, commands применяется к последней установленной точке останова.

С помощью команд точки останова можно возобновить выполнение программы. Для этого достаточно использовать команду continue, step или любую другую команду, возобновляющую выполнение.

При указании любой команды, возобновляющей выполнение (сейчас это continue, step, next, return, jump, quit и их сокращения), список команд завершается (как если бы сразу после этой команды следовал конец ввода). Это необходимо, поскольку при каждом возобновлении выполнения (даже при простом переходе к следующей строке или пошаговом выполнении) может встретиться другая точка останова — возможно, со своим списком команд, что создаст неоднозначность относительно того, какой список выполнять.

Если в списке команд используется команда silent, обычное сообщение об остановке на точке останова не выводится. Это может быть удобно для точек останова, которые должны вывести определённое сообщение, а затем продолжить выполнение. Если ни одна из остальных команд ничего не выводит, вы не узнаете, что точка останова сработала.

s(tep)

Выполняет текущую строку и останавливается при первой возможности (либо в вызываемой функции, либо на следующей строке текущей функции).

n(ext)

Продолжает выполнение до следующей строки текущей функции или до её возврата. (Разница между next и step заключается в том, что step останавливается внутри вызванной функции, а next выполняет вызванные функции (почти) на полной скорости и останавливается только на следующей строке текущей функции.)

unt(il) [lineno]

Без аргументов продолжает выполнение до достижения строки с номером больше текущего.

Если указан аргумент lineno, продолжает выполнение до достижения строки с номером, большим или равным lineno. В обоих случаях выполнение также останавливается при возврате из текущего кадра.

Изменено в версии 3.2: Добавлена возможность указывать номер строки.

r(eturn)

Продолжает выполнение до возврата из текущей функции.

c(ont(inue))

Продолжает выполнение и останавливается только при достижении точки останова.

j(ump) lineno

Задаёт следующую исполняемую строку. Доступна только в самом нижнем кадре. Позволяет перейти назад и повторно выполнить код или перейти вперёд, пропустив ненужный код.

Обратите внимание, что разрешены не все переходы: например, нельзя перейти в середину цикла for или выйти из блока finally.

l(ist) [first[, last]]

Выводит исходный код текущего файла. Без аргументов выводит 11 строк вокруг текущей строки или продолжает предыдущий список. Если в качестве аргумента указано ., выводит 11 строк вокруг текущей строки. С одним аргументом выводит 11 строк вокруг указанной строки. С двумя аргументами выводит указанный диапазон; если второй аргумент меньше первого, он считается количеством строк.

Текущая строка текущего кадра отмечается символом ->. Если выполняется отладка исключения, строка, в которой исключение изначально возникло или было передано дальше, отмечается символом >>, если она отличается от текущей строки.

Изменено в версии 3.2: Добавлен маркер >>.

ll | longlist

Выводит весь исходный код текущей функции или кадра. Важные строки отмечаются так же, как и в команде list.

Добавлено в версии 3.2.

a(rgs)

Выводит аргументы текущей функции и их текущие значения.

p expression

Вычисляет expression в текущем контексте и выводит его значение.

Примечание

Также можно использовать print(), но это не команда отладчика — она вызывает функцию Python print().

pp expression

Аналогична команде p, но значение expression выводится в отформатированном виде с помощью модуля pprint.

whatis expression

Выводит тип expression.

source expression

Пытается получить исходный код expression и вывести его.

Добавлено в версии 3.2.

display [expression]

Выводит значение expression, если оно изменилось, при каждой остановке выполнения в текущем кадре.

Если expression не указан, выводит список всех выражений для отображения в текущем кадре.

Примечание

Команда display вычисляет expression и сравнивает результат с результатом предыдущего вычисления expression, поэтому при изменяемом результате она может не обнаружить изменений.

Пример:

lst = []
breakpoint()
pass
lst.append(1)
print(lst)

Команда display не обнаружит, что lst изменилось, поскольку результат вычисления изменяется на месте с помощью lst.append(1) до сравнения:

> example.py(3)<module>()
-> pass
(Pdb) display lst
display lst: []
(Pdb) n
> example.py(4)<module>()
-> lst.append(1)
(Pdb) n
> example.py(5)<module>()
-> print(lst)
(Pdb)

Чтобы это исправить, можно применить некоторые приёмы копирования:

> example.py(3)<module>()
-> pass
(Pdb) display lst[:]
display lst[:]: []
(Pdb) n
> example.py(4)<module>()
-> lst.append(1)
(Pdb) n
> example.py(5)<module>()
-> print(lst)
display lst[:]: [1]  [old: []]
(Pdb)

Добавлено в версии 3.2.

undisplay [expression]

Перестаёт выводить expression в текущем кадре. Если expression не указан, удаляет все выражения для отображения в текущем кадре.

Добавлено в версии 3.2.

interact

Запускает интерактивный интерпретатор (с использованием модуля code), в глобальном пространстве имён которого содержатся все имена (глобальные и локальные), найденные в текущей области видимости.

Добавлено в версии 3.2.

alias [name [command]]

Создаёт псевдоним с именем name, выполняющий command. Command не нужно заключать в кавычки. Заменяемые параметры можно обозначить с помощью %1, %2 и так далее; %* заменяется всеми параметрами. Если command не указан, отображается текущий псевдоним для name. Если аргументы не указаны, выводятся все псевдонимы.

Псевдонимы могут быть вложенными и содержать всё, что допустимо вводить в приглашении pdb. Обратите внимание: псевдонимы могут переопределять внутренние команды pdb. В этом случае такая команда становится недоступной, пока псевдоним не будет удалён. Подстановка псевдонимов рекурсивно применяется к первому слову командной строки; остальные слова не изменяются.

В качестве примера приведены два полезных псевдонима (особенно если поместить их в файл .pdbrc):

# Print instance variables (usage "pi classInst")
alias pi for k in %1.__dict__.keys(): print(f"%1.{k} = {%1.__dict__[k]}")
# Print instance variables in self
alias ps pi self
unalias name

Удаляет указанный псевдоним name.

! statement

Выполняет однострочную инструкцию в контексте текущего кадра стека. Восклицательный знак можно опустить, если только первое слово инструкции не похоже на команду отладчика, например:

(Pdb) ! n=42
(Pdb)

Чтобы задать глобальную переменную, можно предварить команду присваивания инструкцией global в той же строке, например:

(Pdb) global list_options; list_options = ['-l']
(Pdb)
run [args ...]
restart [args ...]

Перезапускает отлаживаемую программу Python. Если указано значение args, оно разбивается с помощью shlex, а результат используется как новое значение sys.argv. История, точки останова, действия и параметры отладчика сохраняются. restart — это псевдоним команды run.

q(uit)

Выходит из отладчика. Выполняемая программа прерывается.

debug code

Запускает рекурсивный отладчик, который пошагово выполняет code (произвольное выражение или инструкцию, выполняемую в текущем окружении).

retval

Выводит возвращаемое значение при последнем возврате из текущей функции.

Сноски

[1]

Принадлежность кадра к определённому модулю определяется значением __name__ в глобальных переменных кадра.

© 2001–2024 Python Software Foundation
Licensed under the PSF License.
https://docs.python.org/3.12/library/pdb.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API