From 8064156562a4c9a4054889c27f595d363b1ab8e3 Mon Sep 17 00:00:00 2001
From: Nao Pross <np@0hm.ch>
Date: Mon, 19 Oct 2020 08:34:18 +0200
Subject: Fix GUI log handler crash

As suspected, logging.Handler works on another thread causing a
crash when widgets are accessed
---
 gui.py | 36 ++++++++++++++++++++----------------
 1 file changed, 20 insertions(+), 16 deletions(-)

diff --git a/gui.py b/gui.py
index cf57a1e..0be9b21 100644
--- a/gui.py
+++ b/gui.py
@@ -11,7 +11,7 @@ import logging
 
 from PyQt5.QtGui import QFont
 from PyQt5.Qt import QStyle
-from PyQt5.QtCore import Qt, QThread, pyqtSlot, pyqtSignal
+from PyQt5.QtCore import Qt, QThread, pyqtSlot, pyqtSignal, QObject
 from PyQt5.QtWidgets import QApplication, QWidget, QTreeWidget, QTreeWidgetItem, QTreeWidgetItemIterator, QGridLayout, QHBoxLayout, QPushButton, QProgressBar, QTabWidget, QPlainTextEdit
 
 import moodle
@@ -203,19 +203,12 @@ class MoodleTreeView(QTreeWidget):
         self.sortByColumn(0, Qt.AscendingOrder)
         self.setSortingEnabled(True)
 
-# FIXME: I bet this logger is in another thread and f*cks up
-class QPlainTextEditLogger(logging.Handler):
-    def __init__(self, parent):
-        super().__init__()
-        font = QFont("Monospace")
-        font.setStyleHint(QFont.Monospace)
-        self.widget = QPlainTextEdit(parent)
-        self.widget.setReadOnly(True)
-        self.widget.setFont(font)
+class QLogHandler(QObject, logging.Handler):
+    newLogMessage = pyqtSignal(str)
 
     def emit(self, record):
         msg = self.format(record)
-        self.widget.appendPlainText(msg)
+        self.newLogMessage.emit(msg)
 
     def write(self, m):
         pass
@@ -250,15 +243,26 @@ class Muddle(QTabWidget):
         self.tabmoodle.layout().addWidget(self.tabmoodle.progressbar, 2, 0, 1, -1)
 
         # log tabs
-        handler = QPlainTextEditLogger(self)
-        handler.setFormatter(logging.Formatter("%(name)s - %(levelname)s - %(message)s"))
-        logging.getLogger("muddle").addHandler(handler)
+        self.loghandler = QLogHandler(self)
+        self.loghandler.setFormatter(logging.Formatter("%(name)s - %(levelname)s - %(message)s"))
+        self.loghandler.newLogMessage.connect(self.onNewLogMessage)
+        logging.getLogger("muddle").addHandler(self.loghandler)
+
+        font = QFont("Monospace")
+        font.setStyleHint(QFont.Monospace)
 
-        self.tablogs = handler.widget
-        self.addTab(self.tablogs, "Logs")
+        self.logtext = QPlainTextEdit()
+        self.logtext.setReadOnly(True)
+        self.logtext.setFont(font)
+
+        self.addTab(self.logtext, "Logs")
 
         self.show()
 
+    @pyqtSlot(str)
+    def onNewLogMessage(self, msg):
+        self.logtext.appendPlainText(msg)
+
 
 def start(instance_url, token):
     app = QApplication(sys.argv)
-- 
cgit v1.2.1