27.1. bdb - 调试器框架

源代码: Lib / bdb.py

bdb模块处理基本调试器函数,如设置断点或通过调试器管理执行。

定义了以下异常:

exception bdb.BdbQuit

用于退出调试器的Bdb类引发的异常。

bdb模块还定义了两个类:

class bdb.Breakpoint(self, file, line, temporary=0, cond=None, funcname=None)

此类实现临时断点,忽略计数,禁用和(重新)启用和条件。

断点通过bpbynumber(文件, 行)的列表通过bplist前者指向Breakpoint类的单个实例。后者指向此类实例的列表,因为每行可能有多个断点。

创建断点时,其关联的文件名应为规范形式。如果定义了funcname,则当执行该函数的第一行时,将计算断点命中。条件断点总是计算命中。

Breakpoint实例具有以下方法:

deleteMe()

从与文件/行关联的列表中删除断点。如果它是该位置中的最后一个断点,它还会删除文件/行的条目。

enable()

将断点标记为已启用。

disable()

将断点标记为禁用。

bpformat()

返回一个包含断点的所有信息的字符串,格式很好:

  • 断点号。
  • 如果是临时的或不是。
  • 其文件,行位置。
  • 导致中断的条件。
  • 如果必须忽略下一个N次。
  • 断点命中计数。

版本3.2中的新功能。

bpprint(out=None)

bpformat()的输出打印到文件输出或如果None输出到标准输出。

class bdb.Bdb(skip=None)

Bdb类充当通用的Python调试器基类。

这个类负责跟踪设施的细节;派生类应该实现用户交互。标准调试器类(pdb.Pdb)是一个示例。

如果给定了skip参数,则必须是可重复的glob样式模块名称模式。调试器不会步入到源于与这些模式之一匹配的模块中的帧。帧是否被认为源于某个模块由帧全局中的__name__确定。

版本3.1中的新功能: 跳过参数。

以下方法Bdb通常不需要重写。

canonic(filename)

用于以规范形式获取文件名的辅助方法,即作为案例规范化(在不区分大小写的文件系统上)绝对路径,剥离了周围的尖括号。

reset()

botframestopframereturnframequitting属性设置为准备开始调试。

trace_dispatch(frame, event, arg)

此功能作为调试帧的跟踪功能安装。它的返回值是新的跟踪函数(在大多数情况下,也就是说,它自己)。

默认实现决定如何分派帧,具体取决于将要执行的事件类型(作为字符串传递)。事件可以是以下之一:

  • "line":将执行一行新代码。
  • "call":一个函数即将被调用,或者输入另一个代码块。
  • "return":函数或其他代码块即将返回。
  • "exception":发生异常。
  • "c_call":即将调用C函数。
  • "c_return":返回C函数。
  • "c_exception":C函数引发了异常。

对于Python事件,调用专门的函数(见下文)。对于C事件,不采取任何操作。

arg参数取决于上一个事件。

有关跟踪功能的更多信息,请参阅sys.settrace()的文档。有关代码和框架对象的详细信息,请参阅The standard type hierarchy

dispatch_line(frame)

如果调试器应在当前行上停止,请调用user_line()方法(应在子类中重写)。如果设置了Bdb.quitting标志(可以从user_line()设置),则引发BdbQuit异常。返回对trace_dispatch()方法的引用,以便在该范围中进行进一步跟踪。

dispatch_call(frame, arg)

如果调试器应该在此函数调用上停止,请调用user_call()方法(应在子类中重写)。如果设置了Bdb.quitting标志(可以从user_call()设置),则引发BdbQuit异常。返回对trace_dispatch()方法的引用,以便在该范围中进行进一步跟踪。

dispatch_return(frame, arg)

如果调试器应该在此函数return上停止,调用user_return()方法(应在子类中重写)。如果设置了Bdb.quitting标志(可以从user_return()设置),则引发BdbQuit异常。返回对trace_dispatch()方法的引用,以便在该范围中进行进一步跟踪。

dispatch_exception(frame, arg)

如果调试器应该在此异常停止,调用user_exception()方法(应在子类中重写)。如果设置了Bdb.quitting标志(可以从user_exception()设置),则引发BdbQuit异常。返回对trace_dispatch()方法的引用,以在该范围中进行进一步跟踪。

通常派生类不会覆盖以下方法,但如果他们想重新定义停止和断点的定义,它们可能会被覆盖。

stop_here(frame)

此方法检查是否在调用堆栈中botframe之下。botframe是调试开始的帧。

break_here(frame)

此方法检查在文件名和行中属于frame的断点,或者至少在当前函数中。如果断点是临时断点,则此方法将删除它。

break_anywhere(frame)

此方法检查当前帧的文件名中是否有断点。

派生类应该覆盖这些方法以获得对调试器操作的控制。

user_call(frame, argument_list)

当有可能在被调用函数中的任何位置可能需要中断的可能性时,从dispatch_call()调用此方法。

user_line(frame)

stop_here()break_here()产生True时,从dispatch_line()调用此方法。

user_return(frame, return_value)

stop_here()产生True时,从dispatch_return()调用此方法。

user_exception(frame, exc_info)

stop_here()产生True时,从dispatch_exception()调用此方法。

do_clear(arg)

处理断点如果是临时断点必须删除。

此方法必须由派生类实现。

派生类和客户端可以调用以下方法来影响步进状态。

set_step()

在一行代码后停止。

set_next(frame)

停止在给定帧中或下面的下一行。

set_return(frame)

从给定框架返回时停止。

set_until(frame)

当线路不大于当前线路的线路或从当前帧返回时停止。

set_trace([frame])

开始调试。如果未指定,则从调用者的帧开始调试。

set_continue()

仅在断点处或完成后停止。如果没有断点,请将系统跟踪功能设置为无。

set_quit()

quitting属性设置为True在下一次调用dispatch_*()方法之一时引入BdbQuit

派生类和客户端可以调用以下方法来操作断点。如果出现错误,这些方法将返回包含错误消息的字符串,如果一切正常,则返回None

set_break(filename, lineno, temporary=0, cond, funcname)

设置新的断点。如果对于作为参数传递的filenamelineno行不存在,则返回错误消息。filename应为正则形式,如canonic()方法中所述。

clear_break(filename, lineno)

删除文件名lineno中的断点。如果没有设置,则返回错误消息。

clear_bpbynumber(arg)

删除Breakpoint.bpbynumber中索引为arg的断点。如果arg不是数字或超出范围,则返回错误消息。

clear_all_file_breaks(filename)

删除文件名中的所有断点。如果没有设置,则返回错误消息。

clear_all_breaks()

删除所有现有断点。

get_bpbynumber(arg)

返回由给定数字指定的断点。如果arg是字符串,它将被转换为数字。如果arg是非数字字符串,如果给定的断点从未存在或已被删除,则会引发ValueError

版本3.2中的新功能。

get_break(filename, lineno)

检查文件名lineno是否有断点。

get_breaks(filename, lineno)

返回filenamelineno的所有断点,如果没有设置则返回空列表。

get_file_breaks(filename)

返回filename中的所有断点,如果没有设置,则返回一个空列表。

get_all_breaks()

返回设置的所有断点。

派生类和客户端可以调用以下方法来获取表示堆栈跟踪的数据结构。

get_stack(f, t)

获取帧和所有较高(调用)和较低帧的记录列表,以及较高部分的大小。

format_stack_entry(frame_lineno, lprefix=': ')

返回包含由(frame, lineno)元组标识的堆栈条目的信息的字符串:

  • 包含框架的文件名的规范形式。
  • 函数名称或"<lambda>"
  • 输入参数。
  • 返回值。
  • 代码行(如果存在)。

客户端可以调用以下两种方法来使用调试器调试以字符串形式给出的statement

run(cmd, globals=None, locals=None)

调试通过exec()函数执行的语句。全局默认为__main__.__dict__本地默认为全局

runeval(expr, globals=None, locals=None)

调试通过eval()函数执行的表达式。全局本地的含义与run()中的含义相同。

runctx(cmd, globals, locals)

用于向后兼容。调用run()方法。

runcall(func, *args, **kwds)

调试单个函数调用,并返回其结果。

最后,该模块定义了以下功能:

bdb.checkfuncname(b, frame)

检查我们是否应该在这里断开,这取决于断点b设置的方式。

如果它通过行号设置,它检查b.line是否与框架中也作为参数传递的相同。如果断点是通过函数名设置的,我们必须检查我们是否在正确的框架(正确的函数),如果我们在其第一个可执行行。

bdb.effective(file, line, frame)

确定此行代码是否存在有效(活动)断点。返回一个断点的元组和一个布尔值,指示是否可以删除临时断点。如果没有匹配的断点,返回(无, 无)

bdb.set_trace()

使用调用者框架中的Bdb实例开始调试。