pudbを利用したPythonスクリプトのデバッグ
pudbについて
Pythonのデバッガといえば、謹製のpdbが第一候補にあげられます。
〜 pdbの機能 本家サイト(http://docs.python.jp/2/library/pdb.html) から引用 〜
「 (条件付き)ブレークポイントの設定やソース行レベルでのシングルステップ実行、スタックフレームのインスペクション、ソースコードリスティングおよびいかなるスタックフレームのコンテキストにおける任意のPythonコードの評価をサポートしています。」
pudbはpdbのCUI版と言っても良いくらいの機能を備えている上に、CUIによる使いやすいユーザインターフェイスを備えているのが特徴で、コードリーディングやデバッグに活用できる非常に有効なツールです。
pudbのインストール
pipを利用してpudbをインストールします。
$ pip install pudb Downloading/unpacking pudb Downloading pudb-2014.1.tar.gz (46kB): 46kB downloaded Running setup.py egg_info for package pudb Downloading/unpacking urwid>=1.1.1 (from pudb) Downloading urwid-1.2.1.tar.gz (578kB): 578kB downloaded Running setup.py egg_info for package urwid warning: no files found matching 'CHANGELOG' Downloading/unpacking pygments>=1.0 (from pudb) Downloading Pygments-1.6.tar.gz (1.4MB): 1.4MB downloaded Running setup.py egg_info for package pygments [...] Successfully installed pudb urwid pygments Cleaning up...
pudbを利用する
ここでは以下のサンプルプログラムを例にpudbの操作例を紹介します。
#!/usr/bin/env python #-*- coding: utf-8 -*- import sys class Foo(object): def __init__(self): pass def hello(self, name='stranger'): print 'Hello, %s!' % name def usage(): sys.stderr.write('Usage: hello.py <your name>\n') def main(): foo = Foo() try: foo.hello(sys.argv[1]) except IndexError: usage() sys.exit(1) if __name__ == '__main__': main() ## ## [EOF] ##
pudbコマンドラインオプション
pudbのコマンドラインオプションは以下の通りです。
$ pudb --help Usage: pudb [options] SCRIPT-TO-RUN [SCRIPT-ARGUMENTS] Options: -h, --help show this help message and exit -s, --steal-output --pre-run=COMMAND Run command before each program run
現在(2014/06/24)の時点で -sオプションはNotImplemented となっています。
$ pudb -s hello.py Traceback (most recent call last): File "/Users/saitou/venv/test/bin/pudb", line 9, in <module> load_entry_point('pudb==2014.1', 'console_scripts', 'pudb')() File "/Users/saitou/venv/test/lib/python2.7/site-packages/pudb/run.py", line 30, in main steal_output=options.steal_output) File "/Users/saitou/venv/test/lib/python2.7/site-packages/pudb/__init__.py", line 48, in runscript dbg = _get_debugger(steal_output=steal_output) File "/Users/saitou/venv/test/lib/python2.7/site-packages/pudb/__init__.py", line 35, in _get_debugger dbg = Debugger(**kwargs) File "/Users/saitou/venv/test/lib/python2.7/site-packages/pudb/debugger.py", line 155, in __init__ raise NotImplementedError("output stealing") NotImplementedError: output stealing
pudbを起動する直前に実行するコマンドがあれば --pre-run に指定します。
例えば、lsコマンドを実行したければ --pre-run=/bin/ls のような書式で指定します。
pudbを起動する
pudbは2通りの方法で利用できます。
a) pudbコマンドで起動する
引数にfooを与えてhello.pyを起動します。
$ pudb hello.py foo
b) -m pudb でpythonのオプションとして指定する
$ python -m pudb hello.py foo
初期設定(Ctrl+p)を行う
最初にpudbを起動すると設定画面からスタートします。[Ctrl+p]で随時設定画面を呼び出せます。設定項目は以下の通りです。
主な設定項目
- Line Numbers:
- [x]にした場合は、コードの行番号表示を行う
- Prompt on quit:
- [x]にした場合は、デバッグ対象スクリプトの実行完了後にpudbに処理を戻す
- Shell:
- [!]キーで切り替えるPythonシェルを選択する。カレントシェルに切り替わるclassicがオススメ。
- Theme:
- CUIのテーマ(見た目)を選択する
- Changing this setting requires a restart of PuDB.
- [x] rawを選択しておくと設定変更が即時反映する(ようにみえる)
ヘルプの表示(?)を行う
[?]キーでpudbのヘルプ機能を利用できる。
ヘルプ画面に表示されるpudbのキー操作は以下のとおり
Keys: Ctrl-p - edit preferences n - step over ("next") s - step into c - continue r/f - finish current function t - run to cursor e - show traceback [post-mortem or in exception state] H - move to current line (bottom of stack) u - move up one stack frame d - move down one stack frame o - show console/output screen b - toggle breakpoint m - open module j/k - up/down Ctrl-u/d - page up/down h/l - scroll left/right g/G - start/end L - show (file/line) location / go to line / - search ,/. - search next/previous V - focus variables S - focus stack B - focus breakpoint list C - focus code f1/?/H - show this help screen q - quit Ctrl-c - when in continue mode, break back to PuDB Ctrl-l - redraw screen Command line-related: ! - invoke configured python command line in current environment Ctrl-x - toggle inline command line focus +/- - grow/shrink inline command line (active in command line history) _/= - minimize/maximize inline command line (active in command line history) Ctrl-v - insert newline Ctrl-n/p - browse command line history Tab - yes, there is (simple) tab completion Sidebar-related (active in sidebar): +/- - grow/shrink sidebar _/= - minimize/maximize sidebar [/] - grow/shrink relative size of active sidebar box Keys in variables list: \ - expand/collapse t/r/s/c - show type/repr/str/custom for this variable h - toggle highlighting @ - toggle repetition at top * - toggle private members w - toggle line wrapping n/insert - add new watch expression enter - edit options (also to delete) Keys in stack list: enter - jump to frame Keys in breakpoints view: enter - edit breakpoint d - delete breakpoint e - enable/disable breakpoint
pudbを操作する
pdbと同様に以下のように操作を行う。 変数の値はVariables:ペインに、ステップ実行中のスタック情報はStack:ペインに、設定したブレイクポイントの場所はBreakpoints:ペインにそれぞれ表示されます。
-nキーでステップオーバー -sキーでステップイン -bキーでブレイクポイントの設定 -VキーでVariables:ペインに移動 -SキーでStack:ペインに移動 -BキーでBreakpoints:ペインに移動 -Cキーでメインとなるコードペインに移動 -qでpudbを終了する
pudb操作画面
コマンドラインでpythonコードを実行する
ステップ実行中にCommand line:ペインのPythonシェルから任意のPythonコードを実行可能です。 実行後に[clear]->[Ctrl+x]でコードペインに戻れます。
例 print文で変数の値を表示
例 Fooクラスのhello()メソッドを呼び出す
pudbを終了する
設定でPrompt on quitがチェック[x]されている場合は、終了時にメニューが表示されて、再度実行(Restart)を選択することが可能です。
まとめ
pudbはpdbとほぼ同等の機能を有しています。Command line:ペインの操作の安定性に若干問題がありますが、それを補って余りあるユーザビリティを誇っています。これまでpdbを利用してきた方は一度試してみてください。非常に使いやすくデバッグ作業の効率化に貢献してくれる素敵なツールです。