home *** CD-ROM | disk | FTP | other *** search
Wrap
# Source Generated with Decompyle++ # File: in.pyc (Python 2.6) import pygtk pygtk.require('2.0') import gtk import gtk.gdk as gtk import gtk.glade as gtk import vte import gobject import pango import sys import logging import time import subprocess import apt import apt_pkg import os from DistUpgradeApport import * from DistUpgradeView import DistUpgradeView, FuzzyTimeToStr, InstallProgress, FetchProgress from SimpleGladeApp import SimpleGladeApp, bindtextdomain import gettext from DistUpgradeGettext import gettext as _ def utf8(str): return unicode(str, 'latin1').encode('utf-8') class GtkCdromProgressAdapter(apt.progress.CdromProgress): ''' Report the cdrom add progress Subclass this class to implement cdrom add progress reporting ''' def __init__(self, parent): self.status = parent.label_status self.progress = parent.progressbar_cache self.parent = parent def update(self, text, step): ''' update is called regularly so that the gui can be redrawn ''' if text: self.status.set_text(text) self.progress.set_fraction(step / float(self.totalSteps)) while gtk.events_pending(): gtk.main_iteration() def askCdromName(self): return (False, '') def changeCdrom(self): return False class GtkOpProgress(apt.progress.OpProgress): def __init__(self, progressbar): self.progressbar = progressbar def update(self, percent): self.progressbar.set_fraction(percent / 100) while gtk.events_pending(): gtk.main_iteration() def done(self): self.progressbar.set_text(' ') class GtkFetchProgressAdapter(FetchProgress): def __init__(self, parent): FetchProgress.__init__(self) self.status = parent.label_status self.progress = parent.progressbar_cache self.parent = parent self.canceled = False self.button_cancel = parent.button_fetch_cancel self.button_cancel.connect('clicked', self.cancelClicked) def cancelClicked(self, widget): logging.debug('cancelClicked') self.canceled = True def mediaChange(self, medium, drive): msg = _("Please insert '%s' into the drive '%s'") % (medium, drive) dialog = gtk.MessageDialog(parent = self.parent.window_main, flags = gtk.DIALOG_MODAL, type = gtk.MESSAGE_QUESTION, buttons = gtk.BUTTONS_OK_CANCEL) dialog.set_markup(msg) res = dialog.run() dialog.destroy() if res == gtk.RESPONSE_OK: return True return False def start(self): self.progress.set_fraction(0) self.status.show() self.button_cancel.show() def stop(self): self.progress.set_text(' ') self.status.set_text(_('Fetching is complete')) self.button_cancel.hide() def pulse(self): FetchProgress.pulse(self) self.progress.set_fraction(self.percent / 100) currentItem = self.currentItems + 1 if currentItem > self.totalItems: currentItem = self.totalItems if self.currentCPS > 0: self.status.set_text(_('Fetching file %li of %li at %sB/s') % (currentItem, self.totalItems, apt_pkg.SizeToStr(self.currentCPS))) self.progress.set_text(_('About %s remaining') % FuzzyTimeToStr(self.eta)) else: self.status.set_text(_('Fetching file %li of %li') % (currentItem, self.totalItems)) self.progress.set_text(' ') while gtk.events_pending(): gtk.main_iteration() return not (self.canceled) class GtkInstallProgressAdapter(InstallProgress): TIMEOUT_TERMINAL_ACTIVITY = 240 def __init__(self, parent): InstallProgress.__init__(self) self._cache = None self.label_status = parent.label_status self.progress = parent.progressbar_cache self.expander = parent.expander_terminal self.term = parent._term self.parent = parent reaper = vte.reaper_get() reaper.connect('child-exited', self.child_exited) apt_pkg.Config.Set('DPkg::StopOnError', 'False') def startUpdate(self): InstallProgress.startUpdate(self) self.finished = False self.label_status.set_text(_('Applying changes')) self.progress.set_fraction(0) self.progress.set_text(' ') self.expander.set_sensitive(True) self.term.show() if not os.environ.get('DEBIAN_FRONTEND'): pass frontend = 'gnome' if frontend == 'gnome' and self._cache: if not self._cache.has_key('libgnome2-perl') or not (self._cache['libgnome2-perl'].isInstalled): frontend = 'dialog' self.expander.set_expanded(True) self.env = [ 'VTE_PTY_KEEP_FD=%s' % self.writefd, 'APT_LISTCHANGES_FRONTEND=none'] if not os.environ.has_key('DEBIAN_FRONTEND'): self.env.append('DEBIAN_FRONTEND=%s' % frontend) self.start_time = 0 self.time_ui = 0 self.last_activity = 0 def error(self, pkg, errormsg): InstallProgress.error(self, pkg, errormsg) logging.error("got an error from dpkg for pkg: '%s': '%s'" % (pkg, errormsg)) if gettext.dgettext('dpkg', 'dependency problems - leaving unconfigured') in errormsg: return False self.parent.dialog_error.set_transient_for(self.parent.window_main) summary = _("Could not install '%s'") % pkg msg = _("The upgrade will continue but the '%s' package may be in a not working state. Please consider submitting a bug report about it.") % pkg markup = '<big><b>%s</b></big>\n\n%s' % (summary, msg) self.parent.dialog_error.realize() self.parent.dialog_error.window.set_functions(gtk.gdk.FUNC_MOVE) self.parent.label_error.set_markup(markup) self.parent.textview_error.get_buffer().set_text(utf8(errormsg)) self.parent.scroll_error.show() self.parent.dialog_error.run() self.parent.dialog_error.hide() def conffile(self, current, new): logging.debug("got a conffile-prompt from dpkg for file: '%s'" % current) start = time.time() prim = _("Replace the customized configuration file\n'%s'?") % current sec = _('You will lose any changes you have made to this configuration file if you choose to replace it with a newer version.') markup = '<span weight="bold" size="larger">%s </span> \n\n%s' % (prim, sec) self.parent.label_conffile.set_markup(markup) self.parent.dialog_conffile.set_transient_for(self.parent.window_main) if os.path.exists('/usr/bin/diff'): cmd = [ '/usr/bin/diff', '-u', current, new] diff = utf8(subprocess.Popen(cmd, stdout = subprocess.PIPE).communicate()[0]) self.parent.textview_conffile.get_buffer().set_text(diff) else: self.parent.textview_conffile.get_buffer().set_text(_("The 'diff' command was not found")) res = self.parent.dialog_conffile.run() self.parent.dialog_conffile.hide() self.time_ui += time.time() - start if res == gtk.RESPONSE_YES: self.term.feed_child('y\n') else: self.term.feed_child('n\n') def fork(self): pid = self.term.forkpty(envv = self.env) if pid == 0: for env in self.env: (key, value) = env.split('=') os.environ[key] = value sys.exitfunc = lambda : True return pid def statusChange(self, pkg, percent, status): if self.start_time == 0: self.start_time = time.time() self.progress.set_fraction(float(percent) / 100) self.label_status.set_text(status.strip()) if percent > 1: self.last_activity = time.time() self.activity_timeout_reported = False delta = self.last_activity - self.start_time delta -= self.time_ui time_per_percent = float(delta) / percent eta = (100 - percent) * time_per_percent if eta > 61 and eta < 172800: self.progress.set_text(_('About %s remaining') % FuzzyTimeToStr(eta)) else: self.progress.set_text(' ') def child_exited(self, term, pid, status): self.apt_status = os.WEXITSTATUS(status) self.finished = True def waitChild(self): while not self.finished: self.updateInterface() return self.apt_status def finishUpdate(self): self.label_status.set_text('') def updateInterface(self): try: InstallProgress.updateInterface(self) except ValueError: e = None logging.error("got ValueError from InstallProgress.updateInterface. Line was '%s' (%s)" % (self.read, e)) self.read = '' if self.start_time == 0: self.progress.pulse() time.sleep(0.2) if self.last_activity > 0 and self.last_activity + self.TIMEOUT_TERMINAL_ACTIVITY < time.time(): if not self.activity_timeout_reported: logging.warning('no activity on terminal for %s seconds (%s)' % (self.TIMEOUT_TERMINAL_ACTIVITY, self.label_status.get_text())) self.activity_timeout_reported = True self.parent.expander_terminal.set_expanded(True) while gtk.events_pending(): gtk.main_iteration() time.sleep(0.005) class DistUpgradeVteTerminal(object): def __init__(self, parent, term): self.term = term self.parent = parent def call(self, cmd, hidden = False): def wait_for_child(widget): self.finished = True self.term.show() self.term.connect('child-exited', wait_for_child) self.parent.expander_terminal.set_sensitive(True) if hidden == False: self.parent.expander_terminal.set_expanded(True) self.finished = False pid = self.term.fork_command(command = cmd[0], argv = cmd) if pid < 0: return None while not self.finished: while gtk.events_pending(): gtk.main_iteration() continue pid < 0 time.sleep(0.1) del self.finished class DistUpgradeViewGtk(DistUpgradeView, SimpleGladeApp): ''' gtk frontend of the distUpgrade tool ''' def __init__(self, datadir = None, logdir = None): self.logdir = logdir if not datadir: localedir = os.path.join(os.getcwd(), 'mo') gladedir = os.getcwd() else: localedir = '/usr/share/locale/update-manager' gladedir = os.path.join(datadir, 'glade') try: bindtextdomain('update-manager', localedir) gettext.textdomain('update-manager') except Exception: e = None logging.warning('Error setting locales (%s)' % e) icons = gtk.icon_theme_get_default() try: gtk.window_set_default_icon(icons.load_icon('update-manager', 32, 0)) except gobject.GError: e = None logging.debug('error setting default icon, ignoring (%s)' % e) SimpleGladeApp.__init__(self, gladedir + '/DistUpgrade.glade', None, domain = 'update-manager') self.prev_step = 0 self.icontheme = gtk.icon_theme_get_default() self.pngloader = gtk.gdk.PixbufLoader('png') try: self.svgloader = gtk.gdk.PixbufLoader('svg') self.svgloader.close() except gobject.GError: e = None logging.debug('svg pixbuf loader failed (%s)' % e) self.window_main.realize() self.window_main.window.set_functions(gtk.gdk.FUNC_MOVE) self._opCacheProgress = GtkOpProgress(self.progressbar_cache) self._fetchProgress = GtkFetchProgressAdapter(self) self._cdromProgress = GtkCdromProgressAdapter(self) self._installProgress = GtkInstallProgressAdapter(self) self.details_list = gtk.ListStore(gobject.TYPE_STRING) column = gtk.TreeViewColumn('') render = gtk.CellRendererText() column.pack_start(render, True) column.add_attribute(render, 'markup', 0) self.treeview_details.append_column(column) self.treeview_details.set_model(self.details_list) self.vscrollbar_terminal.set_adjustment(self._term.get_adjustment()) self._term.realize() attrlist = pango.AttrList() attr = pango.AttrScale(pango.SCALE_SMALL, 0, -1) attrlist.insert(attr) self.label_status.set_property('attributes', attrlist) sys.excepthook = self._handleException def _handleException(self, type, value, tb): import traceback lines = traceback.format_exception(type, value, tb) logging.error('not handled expection:\n%s' % '\n'.join(lines)) apport_crash(type, value, tb) if not run_apport(): self.error(_('A fatal error occurred'), _("Please report this as a bug (if you haven't already) and include the files /var/log/dist-upgrade/main.log and /var/log/dist-upgrade/apt.log in your report. The upgrade is now aborted.\nYour original sources.list was saved in /etc/apt/sources.list.distUpgrade."), '\n'.join(lines)) sys.exit(1) def getTerminal(self): return DistUpgradeVteTerminal(self, self._term) def _key_press_handler(self, widget, keyev): if len(keyev.string) == 1 and ord(keyev.string) == 3: summary = _('Ctrl-c pressed') msg = _('This will abort the operation and may leave the system in a broken state. Are you sure you want to do that?') res = self.askYesNoQuestion(summary, msg) logging.warning('ctrl-c press detected, user decided to pass it on: %s', res) return not res return False def create_terminal(self, arg1, arg2, arg3, arg4): ''' helper to create a vte terminal ''' self._term = vte.Terminal() self._term.connect('key-press-event', self._key_press_handler) self._term.set_font_from_string('monospace 10') self._term.connect('contents-changed', self._term_content_changed) self._terminal_lines = [] try: self._terminal_log = open(os.path.join(self.logdir, 'term.log'), 'w') except Exception: e = None self._terminal_log = sys.stdout return self._term def _term_content_changed(self, term): ''' called when the *visible* part of the terminal changes ''' current_text = self._term.get_text((lambda a, b, c, d: True)) new_lines = [] for line in current_text.split('\n'): new_lines.append(line) if line not in self._terminal_lines: self._terminal_log.write(line + '\n') self._terminal_log.flush() continue self._terminal_lines = new_lines def getFetchProgress(self): return self._fetchProgress def getInstallProgress(self, cache): self._installProgress._cache = cache return self._installProgress def getOpCacheProgress(self): return self._opCacheProgress def getCdromProgress(self): return self._cdromProgress def updateStatus(self, msg): self.label_status.set_text('%s' % msg) def hideStep(self, step): image = getattr(self, 'image_step%i' % step) label = getattr(self, 'label_step%i' % step) arrow = getattr(self, 'arrow_step%i' % step) image.hide() label.hide() def showStep(self, step): image = getattr(self, 'image_step%i' % step) label = getattr(self, 'label_step%i' % step) image.show() label.show() def abort(self): size = gtk.ICON_SIZE_MENU step = self.prev_step if step > 0: image = getattr(self, 'image_step%i' % step) arrow = getattr(self, 'arrow_step%i' % step) image.set_from_stock(gtk.STOCK_CANCEL, size) image.show() arrow.hide() def setStep(self, step): if self.icontheme.rescan_if_needed(): logging.debug('icon theme changed, re-reading') size = gtk.ICON_SIZE_MENU attrlist = pango.AttrList() if self.prev_step: image = getattr(self, 'image_step%i' % self.prev_step) label = getattr(self, 'label_step%i' % self.prev_step) arrow = getattr(self, 'arrow_step%i' % self.prev_step) label.set_property('attributes', attrlist) image.set_from_stock(gtk.STOCK_APPLY, size) image.show() arrow.hide() self.prev_step = step image = getattr(self, 'image_step%i' % step) label = getattr(self, 'label_step%i' % step) arrow = getattr(self, 'arrow_step%i' % step) if not label.get_property('visible'): return None arrow.show() image.hide() attr = pango.AttrWeight(pango.WEIGHT_BOLD, 0, -1) attrlist.insert(attr) label.set_property('attributes', attrlist) def information(self, summary, msg, extended_msg = None): self.dialog_information.set_transient_for(self.window_main) msg = '<big><b>%s</b></big>\n\n%s' % (summary, msg) self.label_information.set_markup(msg) if extended_msg != None: buffer = self.textview_information.get_buffer() buffer.set_text(extended_msg) self.scroll_information.show() else: self.scroll_information.hide() self.dialog_information.realize() self.dialog_information.window.set_functions(gtk.gdk.FUNC_MOVE) self.dialog_information.run() self.dialog_information.hide() while gtk.events_pending(): gtk.main_iteration() def error(self, summary, msg, extended_msg = None): self.dialog_error.set_transient_for(self.window_main) msg = '<big><b>%s</b></big>\n\n%s' % (summary, msg) self.label_error.set_markup(msg) if extended_msg != None: buffer = self.textview_error.get_buffer() buffer.set_text(extended_msg) self.scroll_error.show() else: self.scroll_error.hide() self.dialog_error.realize() self.dialog_error.window.set_functions(gtk.gdk.FUNC_MOVE) self.dialog_error.run() self.dialog_error.hide() return False def confirmChanges(self, summary, changes, downloadSize, actions = None, removal_bold = True): if not DistUpgradeView.confirmChanges(self, summary, changes, downloadSize): return False self.confirmChangesMessage += '\n\n<b>%s</b>' % _('To prevent data loss close all open applications and documents.') self.label_summary.set_markup('<big><b>%s</b></big>' % summary) self.label_changes.set_markup(self.confirmChangesMessage) self.details_list.clear() for dg in self.toDowngrade: self.details_list.append([ _('<b>Downgrade %s</b>') % dg]) for rm in self.toRemove: s = _('Remove %s') % rm if removal_bold: s = '<b>%s</b>' % s self.details_list.append([ s]) for inst in self.toInstall: self.details_list.append([ _('Install %s') % inst]) for up in self.toUpgrade: self.details_list.append([ _('Upgrade %s') % up]) self.dialog_changes.set_transient_for(self.window_main) self.dialog_changes.realize() self.treeview_details.realize() self.treeview_details.set_cursor((0,)) self.treeview_details.scroll_to_point(0, 0) self.dialog_changes.window.set_functions(gtk.gdk.FUNC_MOVE) res = self.dialog_changes.run() self.dialog_changes.hide() if res == gtk.RESPONSE_YES: return True return False def askYesNoQuestion(self, summary, msg, default = 'No'): msg = '<big><b>%s</b></big>\n\n%s' % (summary, msg) dialog = gtk.MessageDialog(parent = self.window_main, flags = gtk.DIALOG_MODAL, type = gtk.MESSAGE_QUESTION, buttons = gtk.BUTTONS_YES_NO) if default == 'No': dialog.set_default_response(gtk.RESPONSE_NO) else: dialog.set_default_response(gtk.RESPONSE_YES) dialog.set_markup(msg) res = dialog.run() dialog.destroy() if res == gtk.RESPONSE_YES: return True return False def confirmRestart(self): self.dialog_restart.set_transient_for(self.window_main) self.dialog_restart.realize() self.dialog_restart.window.set_functions(gtk.gdk.FUNC_MOVE) res = self.dialog_restart.run() self.dialog_restart.hide() if res == gtk.RESPONSE_YES: return True return False def processEvents(self): while gtk.events_pending(): gtk.main_iteration() def on_window_main_delete_event(self, widget, event): self.dialog_cancel.set_transient_for(self.window_main) self.dialog_cancel.realize() self.dialog_cancel.window.set_functions(gtk.gdk.FUNC_MOVE) res = self.dialog_cancel.run() self.dialog_cancel.hide() if res == gtk.RESPONSE_CANCEL: sys.exit(1) return True if __name__ == '__main__': view = DistUpgradeViewGtk() fp = GtkFetchProgressAdapter(view) ip = GtkInstallProgressAdapter(view) cache = apt.Cache() for pkg in sys.argv[1:]: if cache[pkg].isInstalled: cache[pkg].markDelete() else: cache[pkg].markInstall() cache.commit(fp, ip) gtk.main() sys.exit(0) ip.conffile('TODO', 'TODO~') view.getTerminal().call([ 'dpkg', '--configure', '-a']) view.error('short', 'long', 'asfds afsdj af asdf asdf asf dsa fadsf asdf as fasf sextended\nasfds afsdj af asdf asdf asf dsa fadsf asdf as fasf sextended\nasfds afsdj af asdf asdf asf dsa fadsf asdf as fasf sextended\nasfds afsdj af asdf asdf asf dsa fadsf asdf as fasf sextended\nasfds afsdj af asdf asdf asf dsa fadsf asdf as fasf sextended\nasfds afsdj af asdf asdf asf dsa fadsf asdf as fasf sextended\nasfds afsdj af asdf asdf asf dsa fadsf asdf as fasf sextended\n') view.confirmChanges('xx', [], 100)