Files
h3n3-jmwright-CQ-Editor/cq_editor/widgets/traceback_viewer.py
2022-09-16 13:52:44 -05:00

98 lines
3.0 KiB
Python

from traceback import extract_tb, format_exception_only
from PyQt5.QtWidgets import (QWidget, QTreeWidget, QTreeWidgetItem, QAction,
QLabel)
from PyQt5.QtCore import Qt, pyqtSlot, pyqtSignal
from ..mixins import ComponentMixin
from ..utils import layout
class TracebackTree(QTreeWidget):
name = 'Traceback Viewer'
def __init__(self,parent):
super(TracebackTree,self).__init__(parent)
self.setHeaderHidden(False)
self.setItemsExpandable(False)
self.setRootIsDecorated(False)
self.setContextMenuPolicy(Qt.ActionsContextMenu)
self.setColumnCount(3)
self.setHeaderLabels(['File','Line','Code'])
self.root = self.invisibleRootItem()
class TracebackPane(QWidget,ComponentMixin):
sigHighlightLine = pyqtSignal(int)
def __init__(self,parent):
super(TracebackPane,self).__init__(parent)
self.tree = TracebackTree(self)
self.current_exception = QLabel(self)
self.current_exception.setStyleSheet(\
"QLabel {color : red; }");
layout(self,
(self.current_exception,
self.tree),
self)
self.tree.currentItemChanged.connect(self.handleSelection)
@pyqtSlot(object,str)
def addTraceback(self,exc_info,code):
self.tree.clear()
if exc_info:
t,exc,tb = exc_info
root = self.tree.root
code = code.splitlines()
tb = [t for t in extract_tb(tb) if '<string>' in t.filename] #ignore highest frames (debug, exec)
for el in tb:
#workaround of the traceback module
if el.line == '':
line = code[el.lineno-1].strip()
else:
line = el.line
root.addChild(QTreeWidgetItem([el.filename,
str(el.lineno),
line]))
exc_name = t.__name__
exc_msg = str(exc)
exc_msg = exc_msg.replace('<', '&lt;').replace('>', '&gt;') #replace <>
self.current_exception.\
setText('<b>{}</b>: {}'.format(exc_name,exc_msg))
# handle the special case of a SyntaxError
if t is SyntaxError:
root.addChild(QTreeWidgetItem(
[exc.filename,
str(exc.lineno),
exc.text.strip() if exc.text else '']
))
else:
self.current_exception.setText('')
@pyqtSlot(QTreeWidgetItem,QTreeWidgetItem)
def handleSelection(self,item,*args):
if item:
f,line = item.data(0,0),int(item.data(1,0))
if '<string>' in f:
self.sigHighlightLine.emit(line)