代码之家  ›  专栏  ›  技术社区  ›  Mert Nuhoglu

无法重写sys.excepthook

  •  8
  • Mert Nuhoglu  · 技术社区  · 15 年前

    我尝试自定义的行为 sys.excepthook 如所描述的 the recipe .

    在IPython中:

    :import pdb, sys, traceback
    :def info(type, value, tb):
    :    traceback.print_exception(type, value, tb)
    :    pdb.pm()
    :sys.excepthook = info
    :--
    >>> x[10] = 5
    -------------------------------------------------
    Traceback (most recent call last):
      File "<ipython console>", line 1, in <module>
    NameError: name 'x' is not defined
    >>>
    

    pdb.pm() 没有被呼叫。似乎 sys.excepthook = info 在我的python 2.5安装中不工作。

    4 回复  |  直到 7 年前
        1
  •  12
  •   Alex Martelli    15 年前

    你使用的ipython不是普通的python交互shell,它本身会捕获所有的异常,不使用sys.excepthook。运行它作为 ipython -pdb 而不仅仅是 ipython ,它将在未捕获的异常时自动调用PDB,就像您试图处理异常挂钩一样。

        2
  •  12
  •   Chris Billington    10 年前

    在你写这篇文章五年后,ipython仍然是这样工作的,所以我想一个解决方案可能对谷歌搜索有用。

    IPython取代 sys.excepthook 每次执行一行代码时,对sys.excepthook的重写都没有效果。而且,伊普生甚至不打电话 例外情况 它捕获所有异常,并在事情发展到这一步之前自行处理它们。

    要在IPython运行时重写异常处理程序,可以对其shell的 showtraceback 方法。例如,下面是我如何重写以给出一个普通的python回溯(因为我不喜欢i python有多冗长):

    def showtraceback(self):
        traceback_lines = traceback.format_exception(*sys.exc_info())
        del traceback_lines[1]
        message = ''.join(traceback_lines)
        sys.stderr.write(message)
    
    import sys
    import traceback
    import IPython
    IPython.core.interactiveshell.InteractiveShell.showtraceback = showtraceback
    

    这在正常终端控制台和Qt控制台中都可以工作。

        3
  •  0
  •   Community CDub    8 年前

    this SO question 确保你的 sitecustomize.py 这会阻止在交互模式下进行调试。

        4
  •  0
  •   Matthias123    7 年前

    在chris answer上展开,您可以使用另一个函数(如decorator)向jupyters showbacktrace添加您自己的功能:

    from IPython.core.interactiveshell import InteractiveShell
    from functools import wraps
    import traceback
    import sys
    
    def change_function(func):
        @wraps(func)
        def showtraceback(*args, **kwargs):
            # extract exception type, value and traceback
            etype, evalue, tb = sys.exc_info()
            if issubclass(etype, Exception):
                print('caught an exception')
            else:
                # otherwise run the original hook
                value = func(*args, **kwargs)
                return value
        return showtraceback
    
    InteractiveShell.showtraceback = change_function(InteractiveShell.showtraceback)
    
    raise IOError