From ba1b105a176e5f62faf9d6d1f4c1a4c19764a2e4 Mon Sep 17 00:00:00 2001 From: Stefan Pluecken Date: Sun, 17 Dec 2006 22:45:57 +0000 Subject: [PATCH] replace software update plugin with a more user friendly approach add an ipkg python class --- lib/python/Components/Ipkg.py | 107 +++++++++++++++++++ lib/python/Components/Makefile.am | 3 +- lib/python/Components/__init__.py | 2 +- .../Plugins/SystemPlugins/SoftwareUpdate/plugin.py | 115 ++++++++++++++++++++- lib/python/Screens/TimerEdit.py | 2 +- lib/python/Screens/__init__.py | 3 +- 6 files changed, 224 insertions(+), 8 deletions(-) create mode 100644 lib/python/Components/Ipkg.py diff --git a/lib/python/Components/Ipkg.py b/lib/python/Components/Ipkg.py new file mode 100644 index 0000000..25e1979 --- /dev/null +++ b/lib/python/Components/Ipkg.py @@ -0,0 +1,107 @@ +from enigma import eConsoleAppContainer + +class Ipkg: + EVENT_INSTALL = 0 + EVENT_DOWNLOAD = 1 + EVENT_INFLATING = 2 + EVENT_CONFIGURING = 3 + EVENT_REMOVE = 4 + EVENT_UPGRADE = 5 + EVENT_LISTITEM = 9 + EVENT_DONE = 10 + EVENT_ERROR = 11 + + CMD_INSTALL = 0 + CMD_LIST = 1 + CMD_REMOVE = 2 + CMD_UPDATE = 3 + CMD_UPGRADE = 4 + + def __init__(self, ipkg = '/usr/bin/ipkg'): + self.ipkg = ipkg + + self.cmd = eConsoleAppContainer() + self.cmd.appClosed.get().append(self.cmdFinished) + self.cmd.dataAvail.get().append(self.cmdData) + self.cache = None + + self.callbackList = [] + self.setCurrentCommand() + + def setCurrentCommand(self, command = None): + self.currentCommand = command + + def runCmd(self, cmd): + print "executing", self.ipkg, cmd + self.cmd.execute(self.ipkg + " " + cmd) + + def cmdFetchList(self, installed_only = False): + self.fetchedList = [] + if installed_only: + self.runCmd("list_installed") + else: + self.runCmd("list") + self.setCurrentCommand(self.CMD_LIST) + + def cmdUpgrade(self, test_only = False): + append = "" + if test_only: + append = " -test" + self.runCmd("upgrade" + append) + self.setCurrentCommand(self.CMD_UPGRADE) + + def cmdUpdate(self): + self.runCmd("update") + self.setCurrentCommand(self.CMD_UPDATE) + + def cmdFinished(self, retval): + self.callCallbacks(self.EVENT_DONE) + + def cmdData(self, data): + print "data:", data + if self.cache is None: + self.cache = data + else: + self.cache += data + + if '\n' in data: + splitcache = self.cache.split('\n') + if self.cache[-1] == '\n': + iteration = splitcache + self.cache = None + else: + iteration = splitcache[:-1] + self.cache = splitcache[-1] + for mydata in iteration: + if mydata != '': + self.parseLine(mydata) + + def parseLine(self, data): + if self.currentCommand == self.CMD_LIST: + item = data.split(' - ', 2) + self.fetchedList.append(item) + self.callCallbacks(self.EVENT_LISTITEM, item) + else: + if data.find('Downloading') == 0: + self.callCallbacks(self.EVENT_DOWNLOAD, data.split(' ', 5)[1].strip()) + elif data.find('Upgrading') == 0: + self.callCallbacks(self.EVENT_UPGRADE, data.split(' ', 1)[1].split(' ')[0]) + elif data.find('Installing') == 0: + self.callCallbacks(self.EVENT_INSTALL, data.split(' ', 1)[1].split(' ')[0]) + elif data.find('Configuring') == 0: + self.callCallbacks(self.EVENT_CONFIGURING, data.split(' ', 1)[1].split(' ')[0]) + elif data.find('An error occurred') == 0: + self.callCallbacks(self.EVENT_ERROR, None) + elif data.find('Failed to download') == 0: + self.callCallbacks(self.EVENT_ERROR, None) + elif data.find('ipkg_download: ERROR:') == 0: + self.callCallbacks(self.EVENT_ERROR, None) + def callCallbacks(self, event, param = None): + for callback in self.callbackList: + callback(event, param) + + def addCallback(self, callback): + self.callbackList.append(callback) + + def getFetchedList(self): + return self.fetchedList \ No newline at end of file diff --git a/lib/python/Components/Makefile.am b/lib/python/Components/Makefile.am index 46cdec4..b51d53f 100644 --- a/lib/python/Components/Makefile.am +++ b/lib/python/Components/Makefile.am @@ -16,4 +16,5 @@ install_PYTHON = \ PluginList.py PluginComponent.py RecordingConfig.py About.py UsageConfig.py \ FIFOList.py ServiceEventTracker.py Input.py TimerSanityCheck.py FileList.py \ MultiContent.py MediaPlayer.py TunerInfo.py VideoWindow.py ChoiceList.py \ - Element.py Playlist.py ParentalControl.py ParentalControlList.py + Element.py Playlist.py ParentalControl.py ParentalControlList.py \ + Ipkg.py diff --git a/lib/python/Components/__init__.py b/lib/python/Components/__init__.py index 60899d4..e44bd07 100644 --- a/lib/python/Components/__init__.py +++ b/lib/python/Components/__init__.py @@ -8,4 +8,4 @@ __all__ = ["ActionMap", "Button", "Clock", "ConfigList", "IPNameserver", "Network", "RFmon", "DiskInfo", "NimManager", "TimerEntry", "Lcd", "EpgList" "ScrollLabel", "Timezones", "HelpMenuList", "TimerSanityCheck", "FileList", "MultiContent", "TunerInfo", "ChoiceList", "Playlist", - "ParentalControl" ] + "ParentalControl", "NIMSimulator" ] diff --git a/lib/python/Plugins/SystemPlugins/SoftwareUpdate/plugin.py b/lib/python/Plugins/SystemPlugins/SoftwareUpdate/plugin.py index e12729b..1ada35e 100644 --- a/lib/python/Plugins/SystemPlugins/SoftwareUpdate/plugin.py +++ b/lib/python/Plugins/SystemPlugins/SoftwareUpdate/plugin.py @@ -1,4 +1,4 @@ -from enigma import * +from enigma import eTimer, quitMainloop from Screens.Screen import Screen from Screens.MessageBox import MessageBox from Components.ActionMap import ActionMap, NumberActionMap @@ -10,6 +10,9 @@ from Screens.Console import Console from Screens.MessageBox import MessageBox from Plugins.Plugin import PluginDescriptor from Screens.ImageWizard import ImageWizard +from Components.Ipkg import Ipkg +from Components.Slider import Slider +from Components.Label import Label import os @@ -162,7 +165,7 @@ class PacketList(GUIComponent): def invalidate(self): self.l.invalidate() -class Ipkg(Screen): +class Ipkg2(Screen): skin = """ @@ -229,9 +232,113 @@ class Ipkg(Screen): self.delayTimer.start(0, 1) else: self.close() + +class UpdatePlugin(Screen): + skin = """ + + + + + + """ + + def __init__(self, session, args = None): + self.skin = UpdatePlugin.skin + Screen.__init__(self, session) + + self.sliderPackages = { "dreambox-dvb-modules": 1, "enigma2": 2, "tuxbox-image-info": 3 } + + self.slider = Slider(0, 4) + self["slider"] = self.slider + self.activityslider = Slider(0, 100) + self["activityslider"] = self.activityslider + self.status = Label("Upgrading Dreambox... Please wait") + self["status"] = self.status + self.package = Label() + self["package"] = self.package + + self.packages = 0 + self.error = 0 + + self.activity = 0 + self.activityTimer = eTimer() + self.activityTimer.timeout.get().append(self.doActivityTimer) + self.activityTimer.start(100, False) + + self.ipkg = Ipkg() + self.ipkg.addCallback(self.ipkgCallback) + + self.updating = True + self.package.setText("Package list update") + self.ipkg.cmdUpdate() + + self["actions"] = ActionMap(["WizardActions"], + { + "ok": self.exit, + "back": self.exit + }, -1) + + def doActivityTimer(self): + self.activity += 1 + if self.activity == 100: + self.activity = 0 + self.activityslider.setValue(self.activity) + + def ipkgCallback(self, event, param): + if event == Ipkg.EVENT_DOWNLOAD: + self.status.setText(_("Downloading")) + elif event == Ipkg.EVENT_UPGRADE: + if self.sliderPackages.has_key(param): + self.slider.setValue(self.sliderPackages[param]) + self.package.setText(param) + self.status.setText(_("Upgrading")) + self.packages += 1 + elif event == Ipkg.EVENT_INSTALL: + self.package.setText(param) + self.status.setText(_("Installing")) + self.packages += 1 + elif event == Ipkg.EVENT_CONFIGURING: + self.package.setText(param) + self.status.setText(_("Configuring")) + elif event == Ipkg.EVENT_ERROR: + self.error += 1 + elif event == Ipkg.EVENT_DONE: + if self.updating: + self.updating = False + self.ipkg.cmdUpgrade(test_only = False) + elif self.error == 0: + self.slider.setValue(4) + + self.activityTimer.stop() + self.activityslider.setValue(0) + + self.package.setText("") + self.status.setText(_("Done - Installed or upgraded %d packages") % self.packages) + else: + self.activityTimer.stop() + self.activityslider.setValue(0) + error = _("your dreambox might be unusable now. Please consult the manual for further assistance before rebooting your dreambox.") + if self.packages == 0: + error = _("No packages were upgraded yet. So you can check your network and try again.") + if self.updating: + error = _("Your dreambox isn't connected to the internet properly. Please check it and try again.") + self.status.setText(_("Error") + " - " + error) + #print event, "-", param + pass + + def exit(self): + if self.packages != 0 and self.error == 0: + self.session.openWithCallback(self.exitAnswer, MessageBox, _("Upgrade finished. Do you want to reboot your Dreambox?")) + else: + self.close() + + def exitAnswer(self, result): + if result is not None and result: + quitMainloop(2) + self.close() def UpgradeMain(session, **kwargs): - session.open(UpdatePluginMenu) + session.open(UpdatePlugin) def Plugins(**kwargs): - return PluginDescriptor(name="Softwareupdate", description="Updates your receiver's software", icon="update.png", where = PluginDescriptor.WHERE_PLUGINMENU, fnc=UpgradeMain) + return PluginDescriptor(name="Softwareupdate", description=_("Updates your receiver's software"), icon="update.png", where = PluginDescriptor.WHERE_PLUGINMENU, fnc=UpgradeMain) diff --git a/lib/python/Screens/TimerEdit.py b/lib/python/Screens/TimerEdit.py index dbf3f1b..5532dc8 100644 --- a/lib/python/Screens/TimerEdit.py +++ b/lib/python/Screens/TimerEdit.py @@ -199,7 +199,7 @@ class TimerSanityConflict(Screen): if len(timer) > 1: self["timer2"] = TimerList(self.getTimerList(timer[1])) else: - self["timer2"] = Button("No conflict") + self["timer2"] = TimerList([]) self.list = [] count = 0 diff --git a/lib/python/Screens/__init__.py b/lib/python/Screens/__init__.py index 6e57497..0780ced 100644 --- a/lib/python/Screens/__init__.py +++ b/lib/python/Screens/__init__.py @@ -6,4 +6,5 @@ __all__ = ["ChannelSelection", "ClockDisplay", "ConfigMenu", "EpgSelection", "EventView", "Standby", "ServiceInfo", "InfoBarGenerics", "HelpMenu", "Wizard", "PiPSetup", "PVRState", "Console", "InputBox", "ChoiceBox", "SimpleSummary", - "TimerSelection", "SubservicesQuickzap", "ParentalControlSetup" ] + "TimerSelection", "SubservicesQuickzap", "ParentalControlSetup", + "SleepTimerEdit" ] -- 2.7.4