pdb
— 파이썬 디버거¶
소스 코드: Lib/pdb.py
pdb
모듈은 파이썬 프로그램을 위한 대화형 소스 코드 디버거를 정의합니다. 소스 라인 단계의 중단점(breakpoint) 및 단계 실행(single stepping) 설정, 스택 프레임 검사, 소스 코드 목록, 그리고 모든 스택 프레임의 컨텍스트에서 임의의 파이썬 코드 평가를 지원합니다. 또한 포스트-모템(post-mortem) 디버깅을 지원하며, 프로그램 제어 하에서도 호출될 수 있습니다.
이 디버거는 확장이 가능합니다 – 디버거는 실제로 Pdb
클래스로 정의됩니다. 현재 문서화되어 있진 않지만, 소스를 읽어보시면 쉽게 이해하실 수 있습니다. 확장 인터페이스는 bdb
와 cmd
모듈을 활용합니다.
디버거의 프롬프트는 (Pdb)
입니다. 디버거 제어하에 프로그램을 실행하는 일반적인 사용법은 다음과 같습니다:
>>> import pdb
>>> import mymodule
>>> pdb.run('mymodule.test()')
> <string>(0)?()
(Pdb) continue
> <string>(1)?()
(Pdb) continue
NameError: 'spam'
> <string>(1)?()
(Pdb)
버전 3.3에서 변경: readline
모듈을 통한 탭-완성은 명령과 명령 인자에 사용할 수 있습니다, 예를 들면, 현재 전역 및 지역 이름들은 p
명령의 인자로 제공됩니다.
pdb.py
는 다른 스크립트를 디버그하기 위한 스크립트로 호출될 수 있습니다. 예를 들면:
python3 -m pdb myscript.py
스크립트로 호출하는 경우, 디버깅 중인 프로그램이 비정상적으로 종료되면 pdb는 자동으로 포스트-모템(post-mortem) 디버깅을 시작합니다. 포스트-모템 디버깅이 끝나면 (또는 프로그램이 정상적으로 종료되면), pdb는 프로그램을 재시작합니다. 자동 재시작은 중단점과 같은 pdb의 상태를 유지하고 대부분의 경우 프로그램 종료 시 디버거를 종료하는 것보다 유용합니다.
버전 3.2에 추가: pdb.py
는 이제 .pdbrc
파일에 주어진 것처럼 명령을 실행하는 -c
옵션을 받을 수 있습니다, 디버거 명령들 을 확인해보세요.
버전 3.7에 추가: pdb.py
는 이제 python3 -m
과 비슷한 모듈을 실행하는 -m
옵션을 받을 수 있습니다. 스크립트와 마찬가지로, 디버거는 모듈의 첫 번째 줄 바로 전에 실행을 일시정지합니다.
실행 중인 프로그램에서 디버거로 진입하는 일반적인 사용법은:
import pdb; pdb.set_trace()
위 코드를 디버거로 진입하고 싶은 구간에 추가하면 됩니다. 그런 다음 이 문장 뒤에 오는 코드를 단계별로 실행하고, continue
명령을 사용하여 디버거 없이 프로그램을 계속 실행할 수 있습니다.
버전 3.7에 추가: 내장 breakpoint()
가, 기본값으로 호출될 때는, import pdb; pdb.set_trace()
를 대신해서 사용할 수 있습니다.
에러가 발생하는 프로그램을 검사하는 일반적인 사용법은 다음과 같습니다:
>>> import pdb
>>> import mymodule
>>> mymodule.test()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "./mymodule.py", line 4, in test
test2()
File "./mymodule.py", line 3, in test2
print(spam)
NameError: spam
>>> pdb.pm()
> ./mymodule.py(3)test2()
-> print(spam)
(Pdb)
이 모듈은 다음과 같은 함수를 정의합니다; 각 함수는 조금 다른 방식으로 디버거로 진입합니다:
-
pdb.
run
(statement, globals=None, locals=None)¶ 디버거 제어하에 statement (주어진 문자열 또는 코드 객체)를 실행합니다. 코드가 실행하기 전에 디버거 프롬프트가 나타납니다; 중단점을 지정하고
continue
를 입력하거나,step
또는next
를 통해 문장을 단계별로 살펴볼 수 있습니다. (이 모든 명령은 아래에 설명되어 있습니다.) 선택적 인자 globals 와 locals는 코드가 실행되는 환경을 구체적으로 명시합니다; 기본적으로는 이 모듈의 딕셔너리__main__
이 사용됩니다. (내장 함수exec()
또는eval()
에 대한 설명 참조.)
-
pdb.
runeval
(expression, globals=None, locals=None)¶ 디버거 제어하에 문자열 또는 코드 객체로 주어진 expression을 평가합니다.
runeval()
이 반환될 때, 표현식의 값을 반환합니다. 그렇지 않으면 이 함수는run()
과 유사한 함수입니다.
-
pdb.
runcall
(function, *args, **kwds)¶ 주어진 인자와 함께 function (문자열이 아닌, 함수 또는 메서드 객체)를 호출합니다.
runcall()
이 반환될 때, 함수 호출로 반환된 값을 반환합니다. 디버거 프롬프트는 함수에 진입하자마자 나타납니다.
-
pdb.
set_trace
(*, header=None)¶ 호출하는 스택 프레임에서 디버거에 진입합니다. 코드가 디버그 되지 않는 경우 일지라도 (예를 들면, assertion이 실패하는 경우), 프로그램의 특정 지점에 중단점을 하드 코딩할 때 유용하게 사용됩니다. header 값을 주면, 디버깅이 시작되기 바로 전에 그 값이 콘솔에 출력됩니다.
버전 3.7에서 변경: 키워드 전용 인자 header.
-
pdb.
post_mortem
(traceback=None)¶ 주어진 traceback 객체의 포스트-모템(post-mortem) 디버깅으로 진입합니다. 만약 traceback이 주어지지 않았다면, 현재 처리되고 있는 하나의 예외를 사용합니다. (기본값을 사용하는 경우 예외는 반드시 처리되고 있어야 합니다.)
-
pdb.
pm
()¶ sys.last_traceback
에서 찾은 traceback 의 포스트-모템(post-mortem) 디버깅으로 진입합니다.
run*
함수와 set_trace()
는 Pdb
클래스를 인스턴스 화하고 같은 이름의 메서드를 호출하는 에일리어스(alias) 입니다. 더 많은 기능에 액세스하려면, 아래를 참고하여 직접 하셔야 합니다:
-
class
pdb.
Pdb
(completekey='tab', stdin=None, stdout=None, skip=None, nosigint=False, readrc=True)¶ Pdb
는 디버거 클래스입니다.completekey, stdin 그리고 stdout 인자는 내부
cmd.Cmd
클래스로 전달됩니다; 자세한 설명은 해당 클래스에서 확인할 수 있습니다.skip 인자가 주어진다면, 반드시 글로브-스타일(glob-style) 모듈 이름 패턴의 이터러블(iterable) 이어야 합니다. 디버거는 이 패턴 중 하나와 일치하는 모듈에서 시작되는 프레임 단계로 들어가지 않습니다. 1
기본적으로, Pdb는 사용자가
continue
명령을 내릴 때, SIGINT 신호(사용자가 콘솔에서 Ctrl-C를 누를 때 전송되는 신호) 에 대한 핸들러를 설정합니다. 사용자는 Ctrl-C를 눌러서 디버거를 벗어날 수 있습니다. 만약 Pdb가 SIGINT 핸들러를 건드리지 않길 원한다면 nosigint 설정을 참으로 변경하면 됩니다.readrc 인자는 기본적으로 참이고 Pdb가 파일 시스템으로부터 .pdbrc를 불러올지 여부를 제어합니다.
skip으로 추적하기 위한 호출 예시:
import pdb; pdb.Pdb(skip=['django.*']).set_trace()
버전 3.1에 추가: skip 인자.
버전 3.2에 추가: nosigint 인자. 이전에는, Pdb가 SIGINT 핸들러를 설정하지 않았습니다.
버전 3.6에서 변경: readrc 인자.
디버거 명령들¶
디버거가 인식할 수 있는 명령이 아래 나열되어 있습니다. 대부분의 명령은 한두 문자로 단축될 수 있습니다; 예를 들면, h(elp)
는 h
또는 help
로 help 명령을 입력할 때 사용할 수 있습니다. (하지만 he
, hel
, H
, Help
또는 HELP
는 사용할 수 없습니다.) 인자는 반드시 명령과 공백(스페이스나 탭)으로 분리되어야 합니다. 선택적 인자는 명령 문법에서 대괄호([]
)로 묶여있습니다; 대괄호는 입력하지 않습니다. 명령 문법에서 대체 가능한 인자는 세로 바(|
)로 분리되어 있습니다.
빈 줄을 입력하면 마지막으로 입력된 명령이 반복됩니다. 예외: 만약 마지막 명령이 list
명령이면, 다음 11줄이 나열됩니다.
디버거가 인식하지 못하는 명령은 파이썬 문장으로 가정하고 디버깅 중인 프로그램의 컨텍스트에서 실행됩니다. 파이썬 문장 앞에 느낌표(!
)를 붙여 사용할 수도 있습니다. 이 방법은 디버깅 중인 프로그램을 검사하는 강력한 방법입니다. 변수를 변경하거나 함수를 호출하는 것도 가능합니다. 이 문장에서 예외가 발생하면, 예외 명은 출력되지만 디버거의 상태는 변경되지 않습니다.
디버거는 에일리어스을 지원합니다. 에일리어스는 검사 중인 컨텍스트에서 특정 수준의 적응성을 허용하는 매개변수를 가질 수 있습니다.
한 줄에 여러 명령은 ;;
로 구분하여 입력할 수 있습니다. (단일 ;
는 파이썬 파서로 전달되는 한 줄에서, 여러 명령을 구분하기 위한 분리 기호이므로 사용되지 않습니다.) 명령을 똑똑하게 분리하진 못합니다; 입력의 맨 처음 ;;
에서 나뉘며, 따옴표로 묶인 문자열 중간에 있더라도 나눠집니다.
만약 파일 .pdbrc
가 사용자의 홈 디렉터리 또는 현재 디렉터리에 있으면, 디버거 프롬프트에서 입력된 것처럼 읽히고 실행됩니다. 이것은 특히 에일리어스에 유용합니다. 만약 두 파일이 모두 존재하면, 홈 디렉터리에 있는 파일이 먼저 읽히고 거기에 정의된 에일리어스는 로컬 파일에 의해 무시될 수 있습니다.
-
h(elp)
[command]
¶ 인자가 없는 경우에는, 사용 가능한 명령 리스트를 출력합니다. command 인자가 주어진 경우에는, 해당 명령의 도움말을 출력합니다.
help pdb
는 전체 문서(pdb
모듈의 독스트링)를 표시합니다. command 인자는 반드시 식별자이어야 하므로,!
명령의 도움말을 얻기 위해서help exec
가 꼭 입력되어야 합니다.
-
w(here)
¶ 가장 최근 프레임을 맨 아래로 하는 스택 트레이스를 출력합니다. 화살표는 현재 프레임을 나타내며, 대부분의 명령의 컨텍스트를 명확히 합니다.
-
d(own)
[count]
¶ 스택 트레이스에서 현재 프레임을 count (기본 1) 단계 아래로 (새로운 프레임으로) 이동합니다.
-
u(p)
[count]
¶ 스택 트레이스에서 현재 프레임을 count (기본 1) 단계 위로 (이전 프레임으로) 이동합니다.
-
b(reak)
[([filename:]lineno | function) [, condition]]
¶ lineno 인자가 주어진 경우, 현재 파일의 해당 줄 번호에 브레이크를 설정합니다. function 인자가 주어진 경우, 함수 내에서 첫 번째 실행 가능한 문장에서 브레이크를 설정합니다. 줄 번호는 다른 파일 (아마도 아직 로드되지 않은 파일)에 중단점을 지정하기 위해, 파일명과 콜론을 접두사로 사용할 수 있습니다. 파일은
sys.path
에서 검색합니다. 주의할 점은 각 중단점에 번호가 지정되며, 다른 모든 중단점 명령이 그 번호를 참조하게 됩니다.두 번째 인자가 있는 경우, 중단점을 적용하기 전에 표현식이 반드시 참이어야 합니다.
인자가 없다면, 각 중단점, 중단점에 도달한 횟수, 현재까지 무시 횟수, 그리고 관련 조건(있는 경우)을 포함한 모든 중단지점을 나열합니다.
-
cl(ear)
[filename:lineno | bpnumber [bpnumber ...]]
¶ filename:lineno 인자가 주어진 경우, 해당 줄에 있는 모든 중단점을 제거합니다. 공백으로 구분된 중단점 번호 배열이 주어진 경우, 해당 중단점을 제거합니다. 인자가 없는 경우, 모든 중단지점을 재차 확인 후 제거합니다.
-
disable
[bpnumber [bpnumber ...]]
¶ 공백으로 구분된 중단점 번호로 해당 중단점을 비활성화합니다. 중단점을 비활성화하는 것은 프로그램이 실행을 중단할 수 없다는 것입니다, 하지만 중단점을 제거하는 것과는 달리, 중단점 목록에 남아있으며 (재-)활성화할 수 있습니다.
-
enable
[bpnumber [bpnumber ...]]
¶ 지정된 중단점을 활성화합니다.
-
ignore
bpnumber [count]
¶ 해당 중단점 번호를 무시할 횟수를 설정합니다. 만약 횟수가 생략된 경우, 무시 횟수는 0으로 설정됩니다. 무시 횟수가 0일 때 중단점이 활성화됩니다. 0이 아닐 때는, 중단점에 도달하고 중단점이 비활성화되지 않고 연관 조건이 참일 때마다 그 횟수가 차감됩니다.
-
condition
bpnumber [condition]
¶ 중단점에 새로운 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
및 해당 명령의 약어들)을 지정하는 것은 (end
명령을 붙인 것처럼) 해당 명령 목록을 끝내는 것입니다. 왜냐하면 실행을 재개할 때마다, 명령 목록을 가진 다른 중단점을 맞이할 수 있고, 어떤 목록을 실행해야 할지 모르는 상황이 생기기 때문입니다.만약 ‘slient’ 명령을 사용하면, 중단점에서 멈출 때 나오는 메시지는 출력되지 않습니다. 특정 메시지를 출력하고 진행되는 중단점에 바람직할 수 있습니다. 다만 그 어떤 명령도 출력하지 않는다면, 그 중단점에 도달했다는 것은 알 수 없습니다.
-
s(tep)
¶ 현재 줄을 실행하고, 멈출 수 있는 가장 첫 번째 줄(호출되는 함수 또는 현재 함수의 다음 줄) 에서 멈춥니다.
-
n(ext)
¶ 현재 함수의 다음 줄에 도달하거나, 반환할 때까지 계속 실행합니다.
next
와step
의 차이점은step
은 호출된 함수 안에서 멈추고,next
는 호출된 함수를 재빠르게 실행하고 현재 함수의 바로 다음 줄에서만 멈춥니다.
-
unt(il)
[lineno]
¶ 인자가 없는 경우에는, 현재 줄 번호보다 높은 줄 번호에 도달할 때까지 계속 실행합니다.
줄 번호가 주어진 경우에는, 해당 번호보다 크거나 같은 줄에 도달할 때까지 계속 실행합니다. 두 경우 모두 현재 프레임이 반환될 때 멈춥니다.
버전 3.2에서 변경: 줄 번호를 명시적으로 줄 수 있도록 허용합니다.
-
r(eturn)
¶ 현재 함수가 반환될 때까지 계속 실행합니다.
-
c(ont(inue))
¶ 중단점을 마주칠 때까지 계속 실행합니다.
-
j(ump)
lineno
¶ 다음으로 실행될 줄을 설정할 수 있습니다. 프레임의 맨 마지막에서만 실행이 가능합니다. 이전 줄로 돌아가 코드를 재실행하거나, 실행을 원치 않는 코드를 건너뛸 수 있습니다.
중요한 점은 이 명령은 언제나 실행할 수 있진 않습니다 –
for
루프 내부로 들어가거나finally
절을 건너뛰는 것은 불가능합니다.
-
l(ist)
[first[, last]]
¶ 현재 파일의 소스 코드를 나열합니다. 인자가 없는 경우, 현재 줄 주위로 11줄을 나열하거나 이전 줄을 이어서 나열합니다. 인자로
.
을 입력한 경우, 현재 줄 주위로 11줄을 나열합니다. 한 인자만 주어진 경우, 해당 줄 주위로 11줄을 나열합니다. 두 인자가 주어진 경우, 두 인자 사이의 모든 줄을 나열합니다; 만약 두 번째 인자가 첫 번째 인자보다 작은 경우, 첫 번째 인자로부터 나열하는 줄 수로 인식합니다.현재 프레임에서 현재 위치는
->
로 표시됩니다. 예외를 디버깅할 때, 예외가 최초로 발생하거나 전파된 줄이 현재 줄과 다른 경우에는>>
로 표시됩니다.버전 3.2에 추가:
>>
표시
-
a(rgs)
¶ 현재 함수의 인자 목록을 출력합니다.
-
p
expression
¶ 현재 컨텍스트에서 expression을 실행하고 값을 출력합니다.
참고
디버거 명령은 아니지만,
print()
도 사용될 수 있습니다 — 이때는 파이썬의print()
함수를 실행하게 됩니다.
-
whatis
expression
¶ expression의 형(type)을 출력합니다.
-
source
expression
¶ 주어진 객체의 소스 코드를 가져와서 보여줍니다.
버전 3.2에 추가.
-
display
[expression]
¶ 현재 프레임에서 실행이 중지될 때마다, 표현식의 값이 변경된 경우 표시합니다.
표현식이 주어지지 않은 경우, 현재 프레임에서 표시되는 모든 표현식을 나열합니다.
버전 3.2에 추가.
-
undisplay
[expression]
¶ 현재 프레임에서 표현식을 더는 표시하지 않습니다. 표현식이 주어지지 않은 경우, 현재 프레임에서 표시되는 모든 표현식을 제거합니다.
버전 3.2에 추가.
-
interact
¶ 현재 스코프에서 찾을 수 있는 모든 지역 또는 전역 이름을 담고 있는 전역 이름 공간을 가진 (
code
모듈을 활용하는) 대화형 인터프리터를 시작합니다.버전 3.2에 추가.
-
alias
[name [command]]
¶ command를 실행하는 name이라 불리는 에일리어스를 생성합니다. 명령은 따옴표로 감싸지 않아도 됩니다. 대체할 수 있는 파라미터는
%1
,%2
등으로 표시되지만,%*
는 모든 파라미터로 대체됩니다. 만약 명령이 주어지지 않으면, 현재 name의 에일리어스가 표시됩니다. 만약 아무 인자가 주어지지 않으면, 모든 에일리어스가 나열됩니다.에일리어스는 중첩될 수 있고 pdb 프롬프트 내에서 정당하게 입력할 수 있는 모든 것을 담을 수 있습니다. 주의할 점은 pdb 내부 명령들이 에일리어스에 의해 오버라이드 될 수 있습니다. 그 명령은 에일리어스가 없어질 때까지 사용할 수 없게 됩니다. 에일리어싱은 명령 줄의 첫 번째 단어에 회귀적으로 적용됩니다; 나머지 단어들은 적용되지 않습니다.
.pdbrc
파일에 추가되면 특히 유용한 두 에일리어스 예시:# Print instance variables (usage "pi classInst") alias pi for k in %1.__dict__.keys(): print("%1.",k,"=",%1.__dict__[k]) # Print instance variables in self alias ps pi self
-
unalias
name
¶ 지정된 에일리어스를 제거합니다.
-
!
statement
¶ 현재 스택 프레임의 컨텍스트에서 단일 statement를 실행합니다. 문장의 첫 단어가 디버거 명령이 아닌 경우, 느낌표는 제외해도 됩니다. 전역 변수를 설정하려면 실행하려는 명령과 동일한 줄 맨 앞에
global
문장을 붙이면 됩니다, 예를 들면:(Pdb) global list_options; list_options = ['-l'] (Pdb)
-
run
[args ...]
¶ -
restart
[args ...]
¶ 디버그 된 파이썬 프로그램을 재시작합니다. 만약 인자가 주어진 경우,
shlex
으로 나뉘게 되고 결과는 새sys.argv
로 사용됩니다. 이전 기록, 중단점, 행동 그리고 디버거 옵션은 유지됩니다.restart
는run
의 에일리어스입니다.
-
q(uit)
¶ 디버거를 종료합니다. 실행되고 있는 프로그램이 종료됩니다.
-
debug
code
¶ Enter a recursive debugger that steps through the code argument (which is an arbitrary expression or statement to be executed in the current environment).
-
retval
¶ -
Print the return value for the last return of a function.
각주
- 1
프레임이 특정 모듈에서 시작되는 것으로 간주하는지 여부는 프레임 전역에 있는
__name__
에 의해 결정됩니다.