From 10456b3f992ae86d837bcf205a1c4006e02c74bd Mon Sep 17 00:00:00 2001 From: Andrew Resch Date: Tue, 13 Nov 2007 08:47:26 +0000 Subject: [PATCH] Add support for Dbus and adding torrents to an already running client. Minor UI tweaks. Additional error checking in update functions. --- TODO | 7 +- deluge/ui/client.py | 15 +- deluge/ui/component.py | 1 - deluge/ui/gtkui/dbusinterface.py | 109 ++ deluge/ui/gtkui/glade/main_window.glade | 1294 +++++++++++------------ deluge/ui/gtkui/gtkui.py | 5 + deluge/ui/gtkui/toolbar.py | 21 +- deluge/ui/gtkui/torrentdetails.py | 68 +- 8 files changed, 823 insertions(+), 697 deletions(-) create mode 100644 deluge/ui/gtkui/dbusinterface.py diff --git a/TODO b/TODO index 75c9bf8cd..6e9b9a488 100644 --- a/TODO +++ b/TODO @@ -15,9 +15,14 @@ * Implement 'Classic' mode * Add remove torrent dialog and ability to remove data * Tray tooltip -* Add DBUS to gtkui so we can add torrents to existing session * Add LSD * Add torrentfiles location config option * Add autoload folder * Add wizard * Add a health indication to the statusbar +* Add sidebar for labels and other things.. Plugins should be able to add their + own section to this. +* Have the dbus interface queue up torrents if we're not connected to a host. + Once connected it should prompt the user if they would like to add the + queued torrents. Maybe add an indicator to the status bar that their are + queued torrents. diff --git a/deluge/ui/client.py b/deluge/ui/client.py index 40edfff4b..d8e2a133f 100644 --- a/deluge/ui/client.py +++ b/deluge/ui/client.py @@ -126,7 +126,13 @@ def is_localhost(): return True return False - + +def connected(): + """Returns True if connected to a host, and False if not.""" + if get_core_uri() != None: + return True + return False + def shutdown(): """Shutdown the core daemon""" try: @@ -146,7 +152,12 @@ def add_torrent_file(torrent_files): for torrent_file in torrent_files: # Open the .torrent file for reading because we need to send it's # contents to the core. - f = open(torrent_file, "rb") + try: + f = open(torrent_file, "rb") + except Exception, e: + log.warning("Unable to open %s: %s", torrent_file, e) + continue + # Get the filename because the core doesn't want a path. (path, filename) = os.path.split(torrent_file) fdump = xmlrpclib.Binary(f.read()) diff --git a/deluge/ui/component.py b/deluge/ui/component.py index 434c83391..23cb5838e 100644 --- a/deluge/ui/component.py +++ b/deluge/ui/component.py @@ -67,7 +67,6 @@ class Component: class ComponentRegistry: def __init__(self): self.components = {} - #self.component_state = {} self.update_timer = None def register(self, name, obj): diff --git a/deluge/ui/gtkui/dbusinterface.py b/deluge/ui/gtkui/dbusinterface.py new file mode 100644 index 000000000..0c91a28e7 --- /dev/null +++ b/deluge/ui/gtkui/dbusinterface.py @@ -0,0 +1,109 @@ +# +# dbusinterface.py +# +# Copyright (C) 2007 Andrew Resch ('andar') +# +# Deluge is free software. +# +# You may redistribute it and/or modify it under the terms of the +# GNU General Public License, as published by the Free Software +# Foundation; either version 2 of the License, or (at your option) +# any later version. +# +# deluge is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. +# See the GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with deluge. If not, write to: +# The Free Software Foundation, Inc., +# 51 Franklin Street, Fifth Floor +# Boston, MA 02110-1301, USA. +# +# In addition, as a special exception, the copyright holders give +# permission to link the code of portions of this program with the OpenSSL +# library. +# You must obey the GNU General Public License in all respects for all of +# the code used other than OpenSSL. If you modify file(s) with this +# exception, you may extend this exception to your version of the file(s), +# but you are not obligated to do so. If you do not wish to do so, delete +# this exception statement from your version. If you delete this exception +# statement from all source files in the program, then also delete it here. + +import sys +import os + +# Import DBUS +#from dbus import Interface, SessionBus, version +import dbus, dbus.service + +if dbus.version >= (0,41,0) and dbus.version < (0,80,0): + import dbus.glib +elif dbus.version >= (0,80,0): + from dbus.mainloop.glib import DBusGMainLoop + DBusGMainLoop(set_as_default=True) + +import deluge.ui.component as component +import deluge.ui.client as client +import deluge.common +from deluge.log import LOG as log + +class DbusInterface(dbus.service.Object, component.Component): + def __init__(self, args, path="/org/deluge_torrent/Deluge"): + component.Component.__init__(self, "DbusInterface") + + # Check to see if the daemon is already running and if not, start it + bus = dbus.SessionBus() + obj = bus.get_object("org.freedesktop.DBus", "/org/freedesktop/DBus") + iface = dbus.Interface(obj, "org.freedesktop.DBus") + if iface.NameHasOwner("org.deluge_torrent.Deluge"): + # Deluge client already running.. Lets exit. + log.info("Deluge already running..") + log.debug("args: %s", args) + # Convert the paths to absolutes + new_args = [] + for arg in args: + if not deluge.common.is_url(arg): + new_args.append(os.path.abspath(arg)) + args = new_args + + # Send the args to the running session + if args != [] and args != None: + bus = dbus.SessionBus() + proxy = bus.get_object("org.deluge_torrent.Deluge", + "/org/deluge_torrent/Deluge") + ui = dbus.Interface(proxy, "org.deluge_torrent.Deluge") + ui.process_args(args) + # Exit + log.debug("Exiting..") + sys.exit(0) + + # Register Deluge with Dbus + log.info("Registering with DBUS..") + bus_name = dbus.service.BusName("org.deluge_torrent.Deluge", + bus=dbus.SessionBus()) + dbus.service.Object.__init__(self, bus_name, path) + + @dbus.service.method("org.deluge_torrent.Deluge", in_signature="as") + def process_args(self, args): + """Process arguments sent to already running Deluge""" + # Pythonize the values from Dbus + dbus_args = args + args = [] + for arg in dbus_args: + args.append(str(arg)) + log.debug("Processing args from other process: %s", args) + for arg in args: + # Check to see if we're connected to a host first + if client.connected(): + if deluge.common.is_url(arg): + log.debug("Attempting to add %s from external source..", + arg) + client.add_torrent_url(arg) + else: + # Just a file + log.debug("Attempting to add %s from external source..", + os.path.abspath(arg)) + client.add_torrent_file([os.path.abspath(arg)]) + diff --git a/deluge/ui/gtkui/glade/main_window.glade b/deluge/ui/gtkui/glade/main_window.glade index a6d21d6ba..ab7c5a27f 100644 --- a/deluge/ui/gtkui/glade/main_window.glade +++ b/deluge/ui/gtkui/glade/main_window.glade @@ -204,7 +204,7 @@ True - False + GTK_ICON_SIZE_SMALL_TOOLBAR True @@ -329,24 +329,19 @@ True - + True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + False + GTK_POLICY_AUTOMATIC + GTK_POLICY_AUTOMATIC + GTK_SHADOW_OUT - + True - False - GTK_POLICY_AUTOMATIC - GTK_POLICY_AUTOMATIC - - - True - True - True - True - False - - + True + True + True + False @@ -356,706 +351,695 @@ - + True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + False - + True - False - True + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + GTK_POLICY_AUTOMATIC + GTK_POLICY_NEVER - + True - True GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - GTK_POLICY_AUTOMATIC - GTK_POLICY_NEVER + GTK_RESIZE_QUEUE + GTK_SHADOW_NONE - + True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - GTK_RESIZE_QUEUE - GTK_SHADOW_NONE + 1 + 2 + 10 - + True - 1 - 2 - 10 + 0 - + True - 0 + 10 + 10 + 15 + 15 - + True - 10 - 10 - 15 - 15 + 5 - + True - 5 + 0.10000000149 + + + False + False + + + + + True + 5 + 4 + 5 - + True - 0.10000000149 + 0 - False - False + 1 + 2 - + True - 5 - 4 - 5 + 0 + + + 3 + 4 + + + + + True + 0 + + + 1 + 2 + 1 + 2 + + + + + True + 0 + + + 3 + 4 + 1 + 2 + + + + + True + 0 + + + 1 + 2 + 2 + 3 + + + + + True + 0 + + + 3 + 4 + 2 + 3 + + + + + True + 0 + + + 1 + 2 + 3 + 4 + + + + + True + 0 + + + 3 + 4 + 3 + 4 + + + + + True + 5 - + + True + 0 + <b>Downloaded:</b> + True + + + + + + + True + 5 + + + True + 0 + <b>Uploaded:</b> + True + + + + + 1 + 2 + + + + + True + 5 + + + True + 0 + <b>Seeders:</b> + True + + + + + 2 + 3 + + + + + True + 5 + + + True + 0 + <b>Share Ratio:</b> + True + + + + + 3 + 4 + + + + + True + 15 + 5 + + + True + 0 + <b>Speed:</b> + True + + + + + 2 + 3 + + + + + True + 15 + 5 + + + True + 0 + <b>Speed:</b> + True + + + + + 2 + 3 + 1 + 2 + + + + + True + 15 + 5 + + + True + 0 + <b>Peers:</b> + True + + + + + 2 + 3 + 2 + 3 + + + + + True + 15 + 5 + + + True + 0 + <b>ETA:</b> + True + + + + + 2 + 3 + 3 + 4 + + + + + True + 0 + 1 + <b>Pieces:</b> + True + + + 4 + 5 + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + True 0 - - 1 - 2 - + + + 1 + 2 + 4 + 5 + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 15 + 5 - - True - 0 - - - 3 - 4 - - - - - True - 0 - - - 1 - 2 - 1 - 2 - - - - - True - 0 - - - 3 - 4 - 1 - 2 - - - - - True - 0 - - - 1 - 2 - 2 - 3 - - - - - True - 0 - - - 3 - 4 - 2 - 3 - - - - - True - 0 - - - 1 - 2 - 3 - 4 - - - - - True - 0 - - - 3 - 4 - 3 - 4 - - - - - True - 5 - - - True - 0 - <b>Downloaded:</b> - True - - - - - - - True - 5 - - - True - 0 - <b>Uploaded:</b> - True - - - - - 1 - 2 - - - - - True - 5 - - - True - 0 - <b>Seeders:</b> - True - - - - - 2 - 3 - - - - - True - 5 - - - True - 0 - <b>Share Ratio:</b> - True - - - - - 3 - 4 - - - - - True - 15 - 5 - - - True - 0 - <b>Speed:</b> - True - - - - - 2 - 3 - - - - - True - 15 - 5 - - - True - 0 - <b>Speed:</b> - True - - - - - 2 - 3 - 1 - 2 - - - - - True - 15 - 5 - - - True - 0 - <b>Peers:</b> - True - - - - - 2 - 3 - 2 - 3 - - - - - True - 15 - 5 - - - True - 0 - <b>ETA:</b> - True - - - - - 2 - 3 - 3 - 4 - - - - + True 0 1 - <b>Pieces:</b> + <b>Availability:</b> True - - 4 - 5 - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - 0 - - - - - 1 - 2 - 4 - 5 - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 15 - 5 - - - True - 0 - 1 - <b>Availability:</b> - True - - - - - 2 - 3 - 4 - 5 - - - - - True - 0 - True - PANGO_WRAP_WORD_CHAR - - - 3 - 4 - 4 - 5 - - - False - 1 + 2 + 3 + 4 + 5 + + + + + True + 0 + True + PANGO_WRAP_WORD_CHAR + + + 3 + 4 + 4 + 5 + + + False + 1 + - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - <b>Statistics</b> - True - - - label_item - - - - - GTK_FILL - - + True GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 0 - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 10 - 10 - 15 - 15 - - - True - 7 - 2 - 2 - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - 0 - 1 - <b># of files:</b> - True - - - - - 3 - 4 - GTK_FILL - - - - - True - 0 - - - 1 - 2 - 3 - 4 - - - - - - True - 0 - - - 1 - 2 - 2 - 3 - - - - - - True - 0 - True - PANGO_WRAP_WORD_CHAR - - - 1 - 2 - - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - 0 - 1 - <b>Total Size:</b> - True - - - - - 2 - 3 - GTK_FILL - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - 0 - 1 - <b>Tracker:</b> - True - - - - - 4 - 5 - GTK_FILL - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - 0 - 1 - <b>Tracker Status:</b> - True - - - - - 5 - 6 - GTK_FILL - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - 0 - 1 - <b>Next Announce:</b> - True - - - - - 6 - 7 - GTK_FILL - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - 0 - 0 - 1 - <b>Name:</b> - True - - - - - GTK_FILL - - - - - True - 0 - True - PANGO_WRAP_WORD_CHAR - - - 1 - 2 - 4 - 5 - - - - - - True - 0 - - - 1 - 2 - 5 - 6 - - - - - - True - 0 - - - 1 - 2 - 6 - 7 - - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 5 - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 0 - <b>Path:</b> - True - - - - - 1 - 2 - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - 0 - True - PANGO_WRAP_WORD_CHAR - - - 1 - 2 - 1 - 2 - - - - - - - - - True - GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK - <b>Torrent Info</b> - True - - - label_item - - + <b>Statistics</b> + True - 1 - 2 - GTK_FILL + label_item + + + GTK_FILL + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 0 + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 10 + 10 + 15 + 15 + + + True + 7 + 2 + 2 + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + + True + 0 + 1 + <b># of files:</b> + True + + + + + 3 + 4 + GTK_FILL + + + + + True + 0 + + + 1 + 2 + 3 + 4 + + + + + + True + 0 + + + 1 + 2 + 2 + 3 + + + + + + True + 0 + True + PANGO_WRAP_WORD_CHAR + + + 1 + 2 + + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + + True + 0 + 1 + <b>Total Size:</b> + True + + + + + 2 + 3 + GTK_FILL + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + + True + 0 + 1 + <b>Tracker:</b> + True + + + + + 4 + 5 + GTK_FILL + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + + True + 0 + 1 + <b>Tracker Status:</b> + True + + + + + 5 + 6 + GTK_FILL + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + + True + 0 + 1 + <b>Next Announce:</b> + True + + + + + 6 + 7 + GTK_FILL + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + + True + 0 + 0 + 1 + <b>Name:</b> + True + + + + + GTK_FILL + + + + + True + 0 + True + PANGO_WRAP_WORD_CHAR + + + 1 + 2 + 4 + 5 + + + + + + True + 0 + + + 1 + 2 + 5 + 6 + + + + + + True + 0 + + + 1 + 2 + 6 + 7 + + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 5 + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 0 + <b>Path:</b> + True + + + + + 1 + 2 + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + 0 + True + PANGO_WRAP_WORD_CHAR + + + 1 + 2 + 1 + 2 + + + + + + + + + True + GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + <b>Torrent Info</b> + True + + + label_item + + + + + 1 + 2 + GTK_FILL + - - False - - - - - True - Details - - - tab - False - False - + + + True + Details + + + tab + False + + False diff --git a/deluge/ui/gtkui/gtkui.py b/deluge/ui/gtkui/gtkui.py index 9a5b0ce27..94a2ac5b2 100644 --- a/deluge/ui/gtkui/gtkui.py +++ b/deluge/ui/gtkui/gtkui.py @@ -51,6 +51,7 @@ from statusbar import StatusBar from connectionmanager import ConnectionManager from signals import Signals from pluginmanager import PluginManager +from dbusinterface import DbusInterface from deluge.configmanager import ConfigManager from deluge.log import LOG as log import deluge.configmanager @@ -86,6 +87,10 @@ DEFAULT_PREFS = { class GtkUI: def __init__(self, args): + # Start the Dbus Interface before anything else.. Just in case we are + # already running. + self.dbusinterface = DbusInterface(args) + # Initialize gettext locale.setlocale(locale.LC_MESSAGES, '') locale.bindtextdomain("deluge", diff --git a/deluge/ui/gtkui/toolbar.py b/deluge/ui/gtkui/toolbar.py index 8d083dedc..7dd7c858e 100644 --- a/deluge/ui/gtkui/toolbar.py +++ b/deluge/ui/gtkui/toolbar.py @@ -175,11 +175,16 @@ class ToolBar(component.Component): # Disable the 'Clear Seeders' button if there's no finished torrent finished = False - selecteds = component.get('TorrentView').get_selected_torrents() - if not selecteds : selecteds = [] + selected = component.get('TorrentView').get_selected_torrents() + if not selected: + selected = [] - for torrent in selecteds : - status = client.get_torrent_status(torrent, ['state'])['state'] + for torrent in selected: + try: + status = client.get_torrent_status(torrent, ['state'])['state'] + except KeyError, e: + log.debug("Error getting torrent state: %s", e) + continue if status == self.STATE_PAUSED: resume = True elif status in [self.STATE_FINISHED, self.STATE_SEEDING]: @@ -187,16 +192,18 @@ class ToolBar(component.Component): pause = True else: pause = True - if pause and resume and finished: break + if pause and resume and finished: + break # Enable the 'Remove Torrent' button only if there's some selected # torrent. - remove = (len(selecteds ) > 0) + remove = (len(selected) > 0) if not finished: torrents = client.get_session_state() for torrent in torrents: - if torrent in selecteds: continue + if torrent in selected: + continue status = client.get_torrent_status(torrent, ['state'])['state'] if status in [self.STATE_FINISHED, self.STATE_SEEDING]: finished = True diff --git a/deluge/ui/gtkui/torrentdetails.py b/deluge/ui/gtkui/torrentdetails.py index b881a8153..4204a110f 100644 --- a/deluge/ui/gtkui/torrentdetails.py +++ b/deluge/ui/gtkui/torrentdetails.py @@ -118,37 +118,43 @@ class TorrentDetails(component.Component): return # We need to adjust the value core gives us for progress - progress = status["progress"]/100 - self.progress_bar.set_fraction(progress) - self.progress_bar.set_text(deluge.common.fpcnt(progress)) - - self.name.set_text(status["name"]) - self.total_size.set_text(deluge.common.fsize(status["total_size"])) - self.num_files.set_text(str(status["num_files"])) - self.pieces.set_text("%s (%s)" % (status["num_pieces"], - deluge.common.fsize(status["piece_length"]))) - self.availability.set_text("%.3f" % status["distributed_copies"]) - self.total_downloaded.set_text("%s (%s)" % \ - (deluge.common.fsize(status["total_done"]), - deluge.common.fsize(status["total_payload_download"]))) - self.total_uploaded.set_text("%s (%s)" % \ - (deluge.common.fsize(status["total_uploaded"]), - deluge.common.fsize(status["total_payload_upload"]))) - self.download_speed.set_text( - deluge.common.fspeed(status["download_payload_rate"])) - self.upload_speed.set_text( - deluge.common.fspeed(status["upload_payload_rate"])) - self.seeders.set_text(deluge.common.fpeer(status["num_seeds"], - status["total_seeds"])) - self.peers.set_text(deluge.common.fpeer(status["num_peers"], - status["total_peers"])) - self.eta.set_text(deluge.common.ftime(status["eta"])) - self.share_ratio.set_text("%.3f" % status["ratio"]) - self.tracker.set_text(status["tracker"]) - self.tracker_status.set_text(status["tracker_status"]) - self.next_announce.set_text( - deluge.common.ftime(status["next_announce"])) - self.torrent_path.set_text(status["save_path"]) + try: + progress = status["progress"]/100 + + self.progress_bar.set_fraction(progress) + self.progress_bar.set_text(deluge.common.fpcnt(progress)) + + self.name.set_text(status["name"]) + self.total_size.set_text( + deluge.common.fsize(status["total_size"])) + self.num_files.set_text(str(status["num_files"])) + self.pieces.set_text("%s (%s)" % (status["num_pieces"], + deluge.common.fsize(status["piece_length"]))) + self.availability.set_text( + "%.3f" % status["distributed_copies"]) + self.total_downloaded.set_text("%s (%s)" % \ + (deluge.common.fsize(status["total_done"]), + deluge.common.fsize(status["total_payload_download"]))) + self.total_uploaded.set_text("%s (%s)" % \ + (deluge.common.fsize(status["total_uploaded"]), + deluge.common.fsize(status["total_payload_upload"]))) + self.download_speed.set_text( + deluge.common.fspeed(status["download_payload_rate"])) + self.upload_speed.set_text( + deluge.common.fspeed(status["upload_payload_rate"])) + self.seeders.set_text(deluge.common.fpeer(status["num_seeds"], + status["total_seeds"])) + self.peers.set_text(deluge.common.fpeer(status["num_peers"], + status["total_peers"])) + self.eta.set_text(deluge.common.ftime(status["eta"])) + self.share_ratio.set_text("%.3f" % status["ratio"]) + self.tracker.set_text(status["tracker"]) + self.tracker_status.set_text(status["tracker_status"]) + self.next_announce.set_text( + deluge.common.ftime(status["next_announce"])) + self.torrent_path.set_text(status["save_path"]) + except KeyError, e: + log.debug(e) def clear(self): # Only update if this page is showing