2010-10-12 106 views
0

有沒有一種方便的方法可以在Python異常上獲取更詳細的堆棧跟蹤?我希望找到一個包裝工具/模塊或其他方式從堆棧跟蹤中獲取更多信息,而不必實際修改生成它的Python腳本。我希望能夠在運行單元測試或doctests時,或者從shell運行實用程序或內聯腳本時使用它。從堆棧跟蹤中獲取更多詳細信息

具體而言,我想我想有局部變量的值,或者可能只是傳遞給堆棧跟蹤中最內層函數的參數的值。一些選項來設置細節級別會很好。

回答

2

不具體涉及您的問題,但你可能會發現這個代碼很有用 - 自動啓動的python調試器發生致命異常時。適合使用交互式代碼。它最初是從ActiveState

# code snippet, to be included in 'sitecustomize.py' 
import sys 

def info(type, value, tb): 
    if hasattr(sys, 'ps1') or not sys.stderr.isatty(): 
     # we are in interactive mode or we don't have a tty-like 
     # device, so we call the default hook 
     sys.__excepthook__(type, value, tb) 
    else: 
     import traceback, pdb 
     # we are NOT in interactive mode, print the exception... 
     traceback.print_exception(type, value, tb) 
     print 
     # ...then start the debugger in post-mortem mode. 
     pdb.pm() 

sys.excepthook = info 
+0

嘿,感謝。我最終將你的代碼封裝在[module](http://pypi.python.org/pypi/coroner)中,以便使用'python -m coroner some_script.py'調用pdb調試。恩,希望沒關係?我在文檔中給出了你的歸屬。我稍後可能會更改模塊以便像我想要的那樣吐出堆棧跟蹤,所以我不必使用pdb將它們挖出來,因此我可以將它用於單元測試等。但與此同時,這可能對某人有用。 – intuited 2010-10-12 08:20:20

+0

嘿,你也可以用'ipython'來做到這一點,我只是意識到。您在傳遞'-c ...'或文件名之前傳遞'-pdb'選項。它似乎不支持'-m ...',但也許可以通過傳遞'/ usr/lib/python ../ runpy.py'作爲文件名來實現。 – intuited 2010-10-12 08:43:45

0

正如mentionned由pyfunc,您可以使用該函數的追蹤模塊,但你只能得到一個堆棧跟蹤。

如果您要檢查堆棧,則必須使用sys.exc_info()函數並步行traceback成員並從其幀(tb_frame)轉儲信息。有關這些類型的更多信息,請參閱python Reference Manual

下面是一個例子:

def killit(a): 
    a[10000000000000] = 1 

def test(a): 
    killit(a) 

def iterate_traceback(tb): 
    while tb is not None: 
     yield tb 
     tb = tb.tb_next 

try: 
    test(tuple()) 
except Exception as e: 

    import sys 
    exception_info = sys.exc_info() 

    traceback = exception_info[2] 
    for tb in iterate_traceback(traceback): 
     print "-" * 10 
     print tb.tb_frame.f_code 
     print tb.tb_frame.f_locals 
     print tb.tb_frame.f_globals