调用ipdb的快捷方式



ipdb非常棒;哇!问题是,当一个脚本崩溃时,我仍然需要在代码中添加四行,这些行不需要大量的输入,但也不是什么都不需要。例如,假设这是一条坏线:

1 = 2

很自然,我得到了这个:

SyntaxError: can't assign to literal

如果出于任何原因,我想调试这一行,看看这一行之前(或当时堆栈中的其他地方)发生了什么,我通常会如下更改这一行代码:

try:
1 = 2
except:
import traceback;traceback.print_exc()
import ipdb;ipdb.set_trace()

这就完成了任务,但我希望能够在"模式"下运行脚本,在这种模式下,无论何时发生任何事情(假设异常未得到处理),我都会得到相同的结果。

那存在吗?

*******编辑*******

由于@np8的响应,我重新编写了驱动程序脚本,如下所示(其中main是任意函数):

if __name__ == "__main__":
start = time.time()
args = parser.parse_args()
if args.verbosity > 1:
from ipdb import launch_ipdb_on_exception
with launch_ipdb_on_exception():
print("Launching ipdb on exception!")
main(start, args)
else:
print("NOT launching ipdb on exception!")
main(start, args)

这使我能够从命令行中确定异常是否应该启动ipdb(即,当我正在开发时)(即,脚本在生产中运行时,因此在本例中使用低于2的详细参数)。

您想要的是"后期调试"。获得所需内容的最简单方法是使用运行脚本

ipdb script.py

python -m pdb script.py

而不是

python script.py

您可以使用launch_ipdb_on_exception上下文管理器:

# test.py
from ipdb import launch_ipdb_on_exception
with launch_ipdb_on_exception():
print(x)

运行以上操作将导致启动ipdb:

python .test.py
NameError("name 'x' is not defined",)
> c:tmpdelete_metest.py(4)<module>()
2
3 with launch_ipdb_on_exception():
----> 4     print(x)
ipdb>

pm是一个函数装饰器,它反映ipdb上下文管理器CCD_ 4。用它来装饰一个函数,如果出现错误,该函数将转到ipdb。名称"pm"来自ipdb.pm()函数,它代表死后,表现相似。

这样,您就可以修饰要使用@pm调试的顶级函数,并且调用堆栈中该级别或更低级别的任何异常都将触发ipdb。

import ipdb

class Decontext(object):
"""
Makes a context manager also act as decorator
"""
def __init__(self, context_manager):
self._cm = context_manager
def __enter__(self):
return self._cm.__enter__()
def __exit__(self, *args, **kwds):
return self._cm.__exit__(*args, **kwds)
def __call__(self, func):
def wrapper(*args, **kwds):
with self:
return func(*args, **kwds)
return wrapper
pm = Decontext(ipdb.launch_ipdb_on_exception())

相关内容

  • 没有找到相关文章

最新更新