我有这样的情况下使用的模块 - 一个进程将运行很长时间,但有时会因未知和不可复制的原因而卡住。它有点hacky,只适用于unix(需要信号):import code, traceback, signaldef debug(sig, frame):
"""Interrupt running process, and provide a python prompt for
interactive debugging."""
d={'_frame':frame} # Allow access to frame object.
d.update(frame.f_globals) # Unless shadowed by global
d.update(frame.f_locals)
i = code.InteractiveConsole(d)
message = "Signal received : entering python shell.\nTraceback:\n"
message += ''.join(traceback.format_stack(frame))
i.interact(message)def listen():
signal.signal(signal.SIGUSR1, debug) # Register handler
要使用,只需在程序启动时调用listen()函数(你甚至可以将它粘贴在site.py中让所有python程序都使用它),并让它运行。在任何时候,使用kill或python发送进程SIGUSR1信号:os.kill(pid, signal.SIGUSR1)
这将导致程序在当前所处的位置中断到python控制台,向您显示堆栈跟踪,并让您操作变量。使用control-d(EOF)继续运行(但请注意,您可能会在发出信号的位置中断任何I / O等,因此它不是完全非侵入式的。
我有另一个脚本执行相同的操作,除了它通过管道与正在运行的进程通信(以允许调试后台进程等)。它有点大,可以在这里发布,但我已将其添加为python cookbook配方。