I this application which has a long running task via ssh, which gets the stdout
then prints this to a wx.TextCtrl
, all this works fine. The problem I have is being able to quit the application, currently when I do the gui hangs. The long sunning ssh task should keep running on the remote server and I just want to close the application. How can I correctly break the while True
loop and also the ssh task when pressing the Quit button?
import wx
import wx.stc as stc
from subprocess import Popen, PIPE, STDOUT
import sys
import spur
import threading
import select
import codecs
import os
import time
import io
class MainWindow(wx.Frame):
def __init__(self, parent, id, title):
wx.Frame.__init__(self, parent, id, title, size=(600, 500), style=wx.DEFAULT_FRAME_STYLE & ~ (wx.RESIZE_BORDER |
wx.RESIZE_BOX |
wx.MAXIMIZE_BOX))
self.running_log = wx.TextCtrl(self, pos=(5, 5), size=(570,390))
self.buttonGo = wx.Button(self, -1, "Go", pos=(180,420))
self.buttonGo.Bind(wx.EVT_BUTTON, self.Go)
self.buttonClose = wx.Button(self, -1, "Quit", pos=(285,420))
self.buttonClose.Bind(wx.EVT_BUTTON, self.OnClose)
self.Show()
self.CreateStatusBar()
menuBar = wx.MenuBar()
menu = wx.Menu()
self.SetMenuBar(menuBar)
self.sshLog1 = sshLog(self)
self.Centre()
self.Show()
def Go(self, event):
threading.Thread(target=self.sshLog1.runCommand).start()
threading.Thread(target=self.sshLog1.readlog1).start()
def OnClose(self, e):
sys.exit()
CloseApp()
class sshLog(wx.Panel):
def __init__(self, parent):
wx.Panel.__init__(self, parent)
self.parent = parent
self.frame = self
def runCommand(self):
self.output_file = io.BytesIO()
shell = spur.SshShell(hostname='10.0.1.1', username='remoteUsername', password='remotePassword', missing_host_key=spur.ssh.MissingHostKey.accept)
process = shell.spawn(['ping', 'google.com', '-t'], stdout=self.output_file)
process.wait_for_result()
def readlog1(self):
while True:
time.sleep(1)
wx.CallAfter(self.readlog2)
def readlog2(self):
last_line = str(self.output_file.getvalue())
wx.CallAfter(self.parent.running_log.AppendText, last_line)
<details class='elided'>
<summary title='Show trimmed content'>···</summary>
###############################
########## CLOSE APP ##########
###############################
class CloseApp(wx.Frame):
def __init__(e):
sys.exit(0)
app = wx.App()
MainWindow(None, -1, 'My App')
app.MainLoop()