system: refactor
checking for updates: doesn't lock the interface, it happens in the background status and moonraker errors are reported in the scrolled window refresh and restart buttons use the busy spinner confirmation when restarting a service during print change the refresh icon to a different one from the restart icons
This commit is contained in:
parent
6cf639c083
commit
726231d4c7
155
panels/system.py
155
panels/system.py
@ -3,39 +3,20 @@ import os
|
||||
import gi
|
||||
|
||||
gi.require_version("Gtk", "3.0")
|
||||
from gi.repository import Gtk, Pango, GLib
|
||||
from gi.repository import Gtk, Pango
|
||||
from ks_includes.screen_panel import ScreenPanel
|
||||
|
||||
|
||||
# Same as ALLOWED_SERVICES in moonraker
|
||||
# https://github.com/Arksine/moonraker/blob/master/moonraker/components/machine.py
|
||||
ALLOWED_SERVICES = (
|
||||
"klipper_mcu",
|
||||
"webcamd",
|
||||
"MoonCord",
|
||||
"klipper",
|
||||
"KlipperScreen",
|
||||
"moonraker",
|
||||
"moonraker-telegram-bot",
|
||||
"moonraker-obico",
|
||||
"sonar",
|
||||
"crowsnest",
|
||||
"octoeverywhere",
|
||||
"ratos-configurator",
|
||||
)
|
||||
|
||||
|
||||
class Panel(ScreenPanel):
|
||||
def __init__(self, screen, title):
|
||||
super().__init__(screen, title)
|
||||
self.refresh = None
|
||||
self.update_dialog = None
|
||||
grid = Gtk.Grid(column_homogeneous=True)
|
||||
self.update_status = None
|
||||
self.system_info = self._screen.apiclient.send_request("machine/system_info")
|
||||
|
||||
update_all = self._gtk.Button('arrow-up', _('Full Update'), 'color1')
|
||||
update_all.connect("clicked", self.show_update_info, "full")
|
||||
update_all.set_vexpand(False)
|
||||
self.refresh = self._gtk.Button('refresh', _('Refresh'), 'color2')
|
||||
self.update_all = self._gtk.Button('arrow-up', _('Full Update'), 'color1')
|
||||
self.update_all.connect("clicked", self.show_update_info, "full")
|
||||
self.update_all.set_vexpand(False)
|
||||
self.refresh = self._gtk.Button('arrow-down', _('Refresh'), 'color2')
|
||||
self.refresh.connect("clicked", self.refresh_updates)
|
||||
self.refresh.set_vexpand(False)
|
||||
|
||||
@ -46,77 +27,80 @@ class Panel(ScreenPanel):
|
||||
shutdown.connect("clicked", self.reboot_poweroff, "poweroff")
|
||||
shutdown.set_vexpand(False)
|
||||
|
||||
scroll = self._gtk.ScrolledWindow()
|
||||
scroll.set_policy(Gtk.PolicyType.NEVER, Gtk.PolicyType.AUTOMATIC)
|
||||
self.update_msg = Gtk.Label(label=_("Checking for updates, please wait..."), vexpand=True)
|
||||
self.moonraker_error_msg = Gtk.Label(label=_("Moonraker update manager is not responding"), vexpand=True)
|
||||
|
||||
self.scroll = self._gtk.ScrolledWindow()
|
||||
self.scroll.set_policy(Gtk.PolicyType.NEVER, Gtk.PolicyType.AUTOMATIC)
|
||||
self.scroll.add(self.update_msg)
|
||||
|
||||
self.main_grid = Gtk.Grid(column_homogeneous=True)
|
||||
self.main_grid.attach(self.scroll, 0, 0, 4, 2)
|
||||
self.main_grid.attach(self.update_all, 0, 2, 1, 1)
|
||||
self.main_grid.attach(self.refresh, 1, 2, 1, 1)
|
||||
self.main_grid.attach(reboot, 2, 2, 1, 1)
|
||||
self.main_grid.attach(shutdown, 3, 2, 1, 1)
|
||||
self.content.add(self.main_grid)
|
||||
|
||||
self._screen._ws.send_method('machine.update.status', callback=self.get_updates)
|
||||
|
||||
def create_info_grid(self):
|
||||
infogrid = Gtk.Grid()
|
||||
infogrid.get_style_context().add_class("system-program-grid")
|
||||
update_resp = self._screen.apiclient.send_request("machine/update/status")
|
||||
for i, prog in enumerate(sorted(list(self.update_status['version_info']))):
|
||||
self.labels[prog] = Gtk.Label(hexpand=True, halign=Gtk.Align.START, ellipsize=Pango.EllipsizeMode.END)
|
||||
|
||||
if not update_resp:
|
||||
self.update_status = {}
|
||||
logging.info("No update manager configured")
|
||||
else:
|
||||
self.update_status = update_resp['result']
|
||||
vi = update_resp['result']['version_info']
|
||||
items = sorted(list(vi))
|
||||
i = 0
|
||||
for prog in items:
|
||||
self.labels[prog] = Gtk.Label(hexpand=True, halign=Gtk.Align.START, ellipsize=Pango.EllipsizeMode.END)
|
||||
self.labels[f"{prog}_status"] = self._gtk.Button()
|
||||
self.labels[f"{prog}_status"].set_hexpand(False)
|
||||
self.labels[f"{prog}_status"].connect("clicked", self.show_update_info, prog)
|
||||
|
||||
self.labels[f"{prog}_status"] = self._gtk.Button()
|
||||
self.labels[f"{prog}_status"].set_hexpand(False)
|
||||
self.labels[f"{prog}_status"].connect("clicked", self.show_update_info, prog)
|
||||
|
||||
if prog in ALLOWED_SERVICES:
|
||||
try:
|
||||
if prog in self.system_info['result']['system_info']['available_services']:
|
||||
self.labels[f"{prog}_restart"] = self._gtk.Button("refresh", scale=.7)
|
||||
self.labels[f"{prog}_restart"].connect("clicked", self.restart, prog)
|
||||
infogrid.attach(self.labels[f"{prog}_restart"], 0, i, 1, 1)
|
||||
except Exception as e:
|
||||
logging.exception(e)
|
||||
|
||||
infogrid.attach(self.labels[f"{prog}_status"], 2, i, 1, 1)
|
||||
self.update_program_info(prog)
|
||||
infogrid.attach(self.labels[prog], 1, i, 1, 1)
|
||||
self.labels[prog].get_style_context().add_class('updater-item')
|
||||
|
||||
infogrid.attach(self.labels[prog], 1, i, 1, 1)
|
||||
self.labels[prog].get_style_context().add_class('updater-item')
|
||||
i = i + 1
|
||||
|
||||
scroll.add(infogrid)
|
||||
|
||||
grid.attach(scroll, 0, 0, 4, 2)
|
||||
grid.attach(update_all, 0, 2, 1, 1)
|
||||
grid.attach(self.refresh, 1, 2, 1, 1)
|
||||
grid.attach(reboot, 2, 2, 1, 1)
|
||||
grid.attach(shutdown, 3, 2, 1, 1)
|
||||
self.content.add(grid)
|
||||
|
||||
def activate(self):
|
||||
self.get_updates()
|
||||
infogrid.attach(self.labels[f"{prog}_status"], 2, i, 1, 1)
|
||||
self.update_program_info(prog)
|
||||
self.scroll.remove(self.update_msg)
|
||||
self.scroll.add(infogrid)
|
||||
|
||||
def refresh_updates(self, widget=None):
|
||||
self.refresh.set_sensitive(False)
|
||||
self._screen.show_popup_message(_("Checking for updates, please wait..."), level=1)
|
||||
GLib.timeout_add_seconds(1, self.get_updates, "true")
|
||||
for child in self.scroll.get_children():
|
||||
self.scroll.remove(child)
|
||||
self.scroll.add(self.update_msg)
|
||||
self._gtk.Button_busy(widget, True)
|
||||
logging.info('Sending machine.update.refresh')
|
||||
self._screen._ws.send_method('machine.update.refresh', callback=self.get_updates)
|
||||
|
||||
def get_updates(self, refresh="false"):
|
||||
update_resp = self._screen.apiclient.send_request(f"machine/update/status?refresh={refresh}", timeout=60)
|
||||
if not update_resp:
|
||||
self.update_status = {}
|
||||
logging.info("No update manager configured")
|
||||
def get_updates(self, response, method, params):
|
||||
self._gtk.Button_busy(self.refresh, False)
|
||||
logging.info(response)
|
||||
if not response or 'result' not in response:
|
||||
self.update_all.set_sensitive(False)
|
||||
self.scroll.remove(self.update_msg)
|
||||
if 'error' in response:
|
||||
self.scroll.add(Gtk.Label(label=f"Moonraker: {response['error']['message']}", vexpand=True))
|
||||
else:
|
||||
self.scroll.add(self.moonraker_error_msg)
|
||||
else:
|
||||
self.update_status = update_resp['result']
|
||||
vi = update_resp['result']['version_info']
|
||||
items = sorted(list(vi))
|
||||
for prog in items:
|
||||
self.update_program_info(prog)
|
||||
self.refresh.set_sensitive(True)
|
||||
self._screen.close_popup_message()
|
||||
self.update_status = response['result']
|
||||
self.update_all.set_sensitive(True)
|
||||
self.create_info_grid()
|
||||
self.scroll.show_all()
|
||||
|
||||
def restart(self, widget, program):
|
||||
if program not in ALLOWED_SERVICES:
|
||||
return
|
||||
|
||||
logging.info(f"Restarting service: {program}")
|
||||
self._screen._ws.send_method("machine.services.restart", {"service": program})
|
||||
if self._printer.state in ["printing", "paused"]:
|
||||
self._screen._confirm_send_action(widget, f'{_("Are you sure?")}\n\n'
|
||||
f'{_("Restart")}: {program}',
|
||||
"machine.services.restart", {"service": program})
|
||||
else:
|
||||
self._screen._send_action(widget, "machine.services.restart", {"service": program})
|
||||
|
||||
def show_update_info(self, widget, program):
|
||||
info = self.update_status['version_info'][program] if program in self.update_status['version_info'] else {}
|
||||
@ -243,7 +227,7 @@ class Panel(ScreenPanel):
|
||||
|
||||
def update_program_info(self, p):
|
||||
|
||||
if 'version_info' not in self.update_status or p not in self.update_status['version_info']:
|
||||
if not self.update_status or p not in self.update_status['version_info']:
|
||||
logging.info(f"Unknown version: {p}")
|
||||
return
|
||||
|
||||
@ -279,7 +263,6 @@ class Panel(ScreenPanel):
|
||||
self._needs_update(p, info['version'], info['remote_version'])
|
||||
|
||||
def _already_updated(self, p, info):
|
||||
logging.info(f"{p} {info['version']}")
|
||||
self.labels[p].set_markup(f"<b>{p}</b>\n{info['version']}")
|
||||
self.labels[f"{p}_status"].set_label(_("Up To Date"))
|
||||
self.labels[f"{p}_status"].get_style_context().remove_class('update')
|
||||
@ -295,17 +278,15 @@ class Panel(ScreenPanel):
|
||||
label = Gtk.Label(wrap=True, hexpand=True, vexpand=True)
|
||||
if method == "reboot":
|
||||
label.set_label(_("Are you sure you wish to reboot the system?"))
|
||||
title = _("Restart")
|
||||
else:
|
||||
label.set_label(_("Are you sure you wish to shutdown the system?"))
|
||||
title = _("Shutdown")
|
||||
buttons = [
|
||||
{"name": _("Host"), "response": Gtk.ResponseType.OK, "style": 'dialog-info'},
|
||||
{"name": _("Printer"), "response": Gtk.ResponseType.APPLY, "style": 'dialog-warning'},
|
||||
{"name": _("Cancel"), "response": Gtk.ResponseType.CANCEL, "style": 'dialog-error'}
|
||||
]
|
||||
if method == "reboot":
|
||||
title = _("Restart")
|
||||
else:
|
||||
title = _("Shutdown")
|
||||
self._gtk.Dialog(title, buttons, label, self.reboot_poweroff_confirm, method)
|
||||
|
||||
def reboot_poweroff_confirm(self, dialog, response_id, method):
|
||||
|
Loading…
x
Reference in New Issue
Block a user