diff options
52 files changed, 3153 insertions, 679 deletions
diff --git a/.bzrignore b/.bzrignore deleted file mode 100644 index 6e92f57..0000000 --- a/.bzrignore +++ /dev/null @@ -1 +0,0 @@ -tags diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..10d85cd --- /dev/null +++ b/.gitignore @@ -0,0 +1,4 @@ +tags +*.pyc +*.so +*.c @@ -1,3 +1,9 @@ +next: + +- allow eix as backend DB +- use an internal messagequeue module instead of external shm +- show the list of world packages + 0.13.1: - fix segfault in GLib - correct config path handling for portage-2.1.7.x diff --git a/doc/TODO b/doc/TODO deleted file mode 100644 index 81c8d5c..0000000 --- a/doc/TODO +++ /dev/null @@ -1,40 +0,0 @@ -Documentation: -============== - -Unittest: -======== - -- ALL! - -Backend: -======== - -- add Paludis support \ -- add pkgcore support |-> not necessairy if catapult is used -- add equo support / - -- rewrite flags handling - -- also check installed packages if they block the current one - -- make sure, a package being removed from the queue is not needed as a dependency by another package -- binary package support - -GUI: -==== - -Main Point: user preferences: - - colors and font sizes - -- rotating systray icon -- if a package has been merged, but there are still dependencies to be merged - move the dependencies up the tree (Updater) -- move GUI prefs out of the system config -- show reverse dependencies -- reload package table when emerge is finished -- show which package has a dependency that causes a block - -[quote] -I would like to be able to see at a glance: -1. How many packages I have installed. (Hopefully in the menubar) -a. How many of the packages are installed, and the number there are in each category. (Just like you do with the queue: "x of y"::"installed of available") -[/quote] diff --git a/doc/TRANSLATING b/doc/TRANSLATING index 4b49fa5..75d1c45 100644 --- a/doc/TRANSLATING +++ b/doc/TRANSLATING @@ -12,15 +12,28 @@ KBabel (kde-base/kbabel) or Gtranslator (app-text/gtranslator). Getting the sources: =================== +You do need the sources to make translations, as the installed program is not sufficient. +Therefore you need to have dev-util/git installed. -You do need the sources to make translations. The installed program is not sufficient. Change into a local directory where you want to have the sources installed. Then do: -> bzr pull lp:portato +> git clone git://github.com/Necoro/portato.git You now should have the actual sources in the "portato" subdirectory. +If you later on want to update these sources, you do: + +> git pull + +Important: If you are working on a given version, you need to change to the correct branch: + +> git checkout -b 0.13 origin/0.13 + +where '0.13' has to be replaced by the version you are going to use. + +Have a look at http://www.git-scm.com for more information on how to use git. + To update an incomplete translation: =================================== diff --git a/epydoc.conf b/epydoc.conf index 62b6c73..0e81aee 100644 --- a/epydoc.conf +++ b/epydoc.conf @@ -27,7 +27,6 @@ sourcecode: yes include-log: no frames: yes css: white -redundant-details: yes # # Project diff --git a/etc/portato.cfg b/etc/portato.cfg index 2429dc7..10f5445 100644 --- a/etc/portato.cfg +++ b/etc/portato.cfg @@ -124,6 +124,7 @@ prefhint = f3f785 ; allowed values: ; - sql : SQLite Database ; - dict : Hashmap in Memory -type = sql +; - eixsql: Eix + SQLite Database +type = eixsql # vim:ts=4:sw=4:noexpandtab:ft=cfg diff --git a/extensions.sh b/extensions.sh new file mode 100755 index 0000000..eb44d92 --- /dev/null +++ b/extensions.sh @@ -0,0 +1,10 @@ +#!/bin/sh + +cflags=$(python -c "from portato.backend import system; print system.get_global_settings('CFLAGS')") + +find -name "*.so" -print0 | xargs -0 rm -f +find -name "*.c" -print0 | xargs -0 rm -f + +CFLAGS=$cflags python setup.py build_ext -i + +rm -rf build diff --git a/i18n/messages.pot b/i18n/messages.pot index aed996a..f148ce2 100644 --- a/i18n/messages.pot +++ b/i18n/messages.pot @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2009-08-31 22:04+0200\n" +"POT-Creation-Date: 2009-08-31 22:12+0200\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n" "Language-Team: LANGUAGE <LL@li.org>\n" @@ -573,7 +573,7 @@ msgstr "" msgid "No %(old)s language file installed. Disable highlighting." msgstr "" -#: portato/gui/views.py:130 plugins/package_details.py:102 +#: portato/gui/views.py:130 plugins/package_details.py:108 #, python-format msgid "Error: %s" msgstr "" @@ -836,6 +836,20 @@ msgstr "" msgid "Update" msgstr "" +#: portato/eix/exceptions.py:26 +msgid "Unknown error." +msgstr "" + +#: portato/eix/exceptions.py:37 +#, python-format +msgid "End of file reached though it was not expected: '%s'" +msgstr "" + +#: portato/eix/exceptions.py:45 +#, python-format +msgid "Version '%s' is not supported." +msgstr "" + #: portato/backend/flags.py:527 #, python-format msgid "Conflicting values for masking status: %s" @@ -867,11 +881,11 @@ msgstr "" msgid "BUG in flags.new_masking_status. It returns '%s'" msgstr "" -#: portato/__init__.py:53 +#: portato/__init__.py:50 msgid "do not fork off as root" msgstr "" -#: portato/__init__.py:76 +#: portato/__init__.py:79 msgid "Starting Portato" msgstr "" @@ -906,31 +920,49 @@ msgid "" "regenerated on each startup." msgstr "" -#: portato/db/__init__.py:40 -msgid "Cannot load SQLDatabase." +#: portato/db/__init__.py:26 +msgid "eix + SQLite" +msgstr "" + +#: portato/db/__init__.py:26 +msgid "" +"Similar to SQLite, but now uses the eix database to get the package " +"information.\n" +"This should be much faster on startup, but requires that your eix database " +"is always up-to-date." msgstr "" -#: portato/db/__init__.py:51 +#: portato/db/__init__.py:41 portato/db/__init__.py:56 #, python-format -msgid "Unknown database type: %s" +msgid "Cannot load %s." msgstr "" -#: portato/db/database.py:38 -msgid "ALL" +#: portato/db/__init__.py:62 +#, python-format +msgid "Unknown database type: %s" msgstr "" -#: portato/db/dict.py:94 +#: portato/db/hash.py:94 #, python-format msgid "" "Catched KeyError => %s seems not to be an available category. Have you " "played with rsync-excludes?" msgstr "" -#: portato/db/dict.py:149 +#: portato/db/hash.py:149 #, python-format msgid "Error while compiling search expression: '%s'." msgstr "" +#: portato/db/eix_sql.py:35 +#, python-format +msgid "Cache file '%s' does not exist. Using default instead." +msgstr "" + +#: portato/db/database.py:38 +msgid "ALL" +msgstr "" + #: portato/db/sql.py:79 msgid "Cleaning database..." msgstr "" @@ -964,133 +996,153 @@ msgstr "" msgid "Unrecognized line in configuration: %s" msgstr "" -#: portato/listener.py:94 +#: portato/listener.py:85 msgid "Listener has not been started." msgstr "" -#: portato/plugin.py:438 portato/plugin.py:441 +#: portato/listener.py:94 +#, python-format +msgid "An exception occured while accessing the message queue: %s" +msgstr "" + +#: portato/plugin.py:446 portato/plugin.py:449 +#, python-format +msgid "Loading plugin module '%(plugin)s' failed: %(error)s" +msgstr "" + +#: portato/plugin.py:459 #, python-format -msgid "Loading plugin '%(plugin)s' failed: %(error)s" +msgid "Loading widgets plugin '%(plugin)s' failed: %(error)s" msgstr "" -#: portato/plugin.py:451 +#: portato/plugin.py:462 +#, python-format +msgid "Loading widgets of plugin '%(plugin)s' failed: %(error)s" +msgstr "" + +#: portato/plugin.py:466 #, python-format msgid "Widgets of plugin '%s' loaded." msgstr "" -#: portato/plugin.py:482 +#: portato/plugin.py:497 msgid "Plugin is disabled!" msgstr "" -#: portato/plugin.py:484 +#: portato/plugin.py:499 msgid "Plugin has unresolved dependencies - disabled!" msgstr "" -#: portato/plugin.py:488 +#: portato/plugin.py:503 #, python-format msgid "Plugin '%s' loaded." msgstr "" -#: portato/plugin.py:528 +#: portato/plugin.py:543 #, python-format msgid "Overriding hook '%(hook)s' with plugin '%(plugin)s'." msgstr "" -#: portato/plugin.py:586 +#: portato/plugin.py:601 #, python-format msgid "" "For hook '%(hook)s' an override is already defined by plugin '%(plugin)s'!" msgstr "" -#: portato/plugin.py:587 +#: portato/plugin.py:602 #, python-format msgid "It is now replaced by the one from plugin '%s'!" msgstr "" -#: portato/plugin.py:620 +#: portato/plugin.py:635 #, python-format msgid "" "Dependant '%(dep)s' for '%(hook)s' in plugin '%(plugin)s' not found! Adding " "nevertheless." msgstr "" -#: plugins/etc_proposals.py:34 +#: portato/plugin.py:704 portato/plugin.py:707 +#, python-format +msgid "Registrating plugin '%(plugin)s' failed: %(error)s" +msgstr "" + +#: plugins/etc_proposals.py:32 msgid "Cannot start etc-proposals. Not root!" msgstr "" -#: plugins/package_details.py:67 +#: plugins/package_details.py:73 msgid "Shows the Changelog of a package" msgstr "" -#: plugins/package_details.py:69 +#: plugins/package_details.py:75 msgid "Changelog" msgstr "" -#: plugins/package_details.py:79 +#: plugins/package_details.py:85 msgid "Shows the ebuild of a package" msgstr "" -#: plugins/package_details.py:82 +#: plugins/package_details.py:88 msgid "Ebuild" msgstr "" -#: plugins/package_details.py:89 +#: plugins/package_details.py:95 msgid "Shows the installed files of a package" msgstr "" -#: plugins/package_details.py:91 +#: plugins/package_details.py:97 msgid "Files" msgstr "" -#: plugins/package_details.py:105 +#: plugins/package_details.py:111 msgid "Shows the dependencies of a package" msgstr "" -#: plugins/package_details.py:107 +#: plugins/package_details.py:113 msgid "Dependencies" msgstr "" -#: plugins/package_details.py:179 +#: plugins/package_details.py:185 #, python-format msgid "If '%s' is disabled" msgstr "" -#: plugins/package_details.py:181 +#: plugins/package_details.py:187 #, python-format msgid "If '%s' is enabled" msgstr "" -#: plugins/package_details.py:187 +#: plugins/package_details.py:193 msgid "One of the following" msgstr "" -#: plugins/package_details.py:192 +#: plugins/package_details.py:198 msgid "All of the following" msgstr "" -#: plugins/package_details.py:203 +#: plugins/package_details.py:209 msgid "" "Can't display dependencies: This package has an unsupported dependency " "string." msgstr "" -#: plugins/notify.py:24 +#: plugins/notify.py:23 msgid "Cannot import 'pynotify'." msgstr "" -#: plugins/notify.py:36 +#: plugins/notify.py:35 msgid "Notify called while process is still running!" msgstr "" -#: plugins/notify.py:40 +#: plugins/notify.py:39 msgid "Emerge finished!" msgstr "" -#: plugins/notify.py:44 +#: plugins/notify.py:43 msgid "Emerge failed!" msgstr "" -#: plugins/notify.py:45 +#: plugins/notify.py:44 #, python-format msgid "Error Code: %d" msgstr "" diff --git a/plugins/etc_proposals.py b/plugins/etc_proposals.py index 83b38f7..052f3d3 100644 --- a/plugins/etc_proposals.py +++ b/plugins/etc_proposals.py @@ -10,8 +10,6 @@ # # Written by René 'Necoro' Neumann <necoro@necoro.net> -from portato.helper import error - import os from subprocess import Popen @@ -31,7 +29,7 @@ class EtcProposals (WidgetPlugin): if os.getuid() == 0: Popen(self.prog+options) else: - error("ETC_PROPOSALS :: %s",_("Cannot start etc-proposals. Not root!")) + helper.error("ETC_PROPOSALS :: %s",_("Cannot start etc-proposals. Not root!")) def hook (self, *args, **kwargs): """Entry point for this plugin.""" diff --git a/plugins/new_version.py b/plugins/new_version.py index 94e61ca..9fa5f4e 100644 --- a/plugins/new_version.py +++ b/plugins/new_version.py @@ -12,16 +12,11 @@ from portato.helper import debug, warning -try: - from bzrlib import plugin, branch -except ImportError: - plugin = branch = None - warning("NEW_VERSION :: Cannot import 'bzrlib'") - +from subprocess import Popen, PIPE import gobject from portato import get_listener -from portato.constants import REPOURI, VERSION, APP_ICON, APP +from portato.constants import REPOURI, REVISION, APP_ICON, APP from portato.gui.utils import GtkThread class NewVersionFinder(WidgetPlugin): @@ -29,7 +24,7 @@ class NewVersionFinder(WidgetPlugin): Checks for a new version of portato every 30 minutes and on startup. """ __author__ = "René 'Necoro' Neumann" - __dependency__ = ["dev-util/bzr"] + __dependency__ = ["dev-util/git"] def init (self): self.add_call("main", self.run) @@ -37,20 +32,30 @@ class NewVersionFinder(WidgetPlugin): def widget_init (self): self.create_widget("Plugin Menu", "Check for new _versions", activate = self.menu) + def get_notify_callback (self, rev): + def callback(): + get_listener().send_notify( + base = "New Portato Live Version Found", + descr = "The most recent revision is %s." % rev, + icon = APP_ICON) + return False + + return callback + def find_version (self, rev): - try: - b = branch.Branch.open(REPOURI) - except Exception, e: - warning("NEW_VERSION :: Exception occured while accessing the remote branch: %s", str(e)) - return - - debug("NEW_VERSION :: Installed rev: %s - Current rev: %s", rev, b.revno()) - if int(rev) < int(b.revno()): - def callback(): - get_listener().send_notify(base = "New Portato Live Version Found", descr = "You have rev. %s, but the most recent revision is %s." % (rev, b.revno()), icon = APP_ICON) - return False - - gobject.idle_add(callback) + + repo, branch = REPOURI.split('::') + + remote_rev = Popen(['git', 'ls-remote', repo, branch], stdout = PIPE).communicate()[0].strip().split('\t') + + if len(remote_rev) and remote_rev[1] not in (branch, 'refs/heads/'+branch, 'refs/tags/'+branch): + warning('NEW_VERSION :: Returned revision information looks strange: %s', str(remote_rev)) + else: + remote_rev = remote_rev[0] + debug("NEW_VERSION :: Installed rev: %s - Current rev: %s", remote_rev, rev) + + if rev != remote_rev: + gobject.idle_add(self.get_notify_callback(remote_rev)) def start_thread(self, rev): t = GtkThread(target = self.find_version, name = "Version Updater Thread", args = (rev,)) @@ -62,16 +67,11 @@ class NewVersionFinder(WidgetPlugin): """ Run the thread once. """ - v = VERSION.split() - if len(v) != 3: + if not REVISION: return None - - rev = v[-1] - - plugin.load_plugins() # to have lp: addresses parsed - self.start_thread(rev) - return rev + self.start_thread(REVISION) + return REVISION def run (self, *args, **kwargs): """ @@ -82,4 +82,4 @@ class NewVersionFinder(WidgetPlugin): if rev is not None: gobject.timeout_add(30*60*1000, self.start_thread, rev) # call it every 30 minutes -register(NewVersionFinder, (branch is None)) +register(NewVersionFinder, REVISION == '') diff --git a/plugins/notify.py b/plugins/notify.py index 3670e20..4aba2c6 100644 --- a/plugins/notify.py +++ b/plugins/notify.py @@ -14,14 +14,13 @@ disable = False from portato import get_listener -from portato.helper import warning, error, debug from portato.constants import APP_ICON, APP try: import pynotify except ImportError: disable = True - warning("NOTIFY :: %s", _("Cannot import 'pynotify'.")) + helper.warning("NOTIFY :: %s", _("Cannot import 'pynotify'.")) class Notify (Plugin): __author__ = "René 'Necoro' Neumann" @@ -33,7 +32,7 @@ class Notify (Plugin): def notify (self, retcode, **kwargs): if retcode is None: - warning("NOTIFY :: %s", _("Notify called while process is still running!")) + helper.warning("NOTIFY :: %s", _("Notify called while process is still running!")) else: icon = APP_ICON if retcode == 0: diff --git a/plugins/package_details.py b/plugins/package_details.py index 6a17f1e..19f3126 100644 --- a/plugins/package_details.py +++ b/plugins/package_details.py @@ -23,13 +23,19 @@ class Detail (WidgetPlugin): """ __author__ = "René 'Necoro' Neumann" + _view_ = None _old_pkg = None + _widget_ = None + _widget_name_ = None def init(self): self.add_call("update_table", self._update, type = "after") def widget_init (self): + if (self._widget_ is None) or (self._widget_name_ is None): + raise PluginLoadException, ("Has not set _widget_ or _widget_name_.") + self.add_widget("Package Notebook", (self._widget_, self._widget_name_)) # if the detail was updated before it was actually initialized, update it again :) diff --git a/portato/__init__.py b/portato/__init__.py index 653329c..98c019d 100644 --- a/portato/__init__.py +++ b/portato/__init__.py @@ -14,15 +14,16 @@ from __future__ import absolute_import import gettext, locale import sys, os -import subprocess, threading -import atexit from optparse import OptionParser, SUPPRESS_HELP -from . import log -from .constants import LOCALE_DIR, APP, VERSION -from .su import detect_su_command +from .log import start as logstart +from .constants import LOCALE_DIR, APP, VERSION, REVISION from .helper import debug, info, error +# set better version info +if REVISION: + VERSION = '%s (git: %s)' % (VERSION, REVISION) + # listener-handling __listener = None @@ -46,7 +47,7 @@ def get_parser (use_ = False): parser = OptionParser(version = vers, prog = "portato", description = desc, usage = usage) - parser.add_option("--shm", action = "store", nargs = 3, type="long", dest = "shm", + parser.add_option("--mq", action = "store", nargs = 1, type="long", dest = "mq", default = None, help = SUPPRESS_HELP) parser.add_option("-F", "--no-fork", action = "store_true", dest = "nofork", default = False, @@ -54,31 +55,34 @@ def get_parser (use_ = False): return parser -def start(): - +def _sub_start (): # set gettext stuff locale.setlocale(locale.LC_ALL, '') gettext.install(APP, LOCALE_DIR, unicode = True) +def start(): + + # set gettext stuff + _sub_start() + # start logging - log.start(file=False) + logstart(file=False) # run parser (options, args) = get_parser().parse_args() - # close listener at exit - atexit.register(get_listener().close) - if options.nofork or os.getuid() == 0: # start GUI - log.start(file = True) # start logging to file + + # close listener at exit + import atexit + atexit.register(get_listener().close) + + logstart(file = True) # start logging to file from .gui import run info("%s v. %s", _("Starting Portato"), VERSION) - if options.shm: - get_listener().set_send(*options.shm) - else: - get_listener().set_send() + get_listener().set_send(options.mq) try: run() @@ -87,14 +91,14 @@ def start(): else: # start us again in root modus and launch listener - import shm_wra |