summaryrefslogtreecommitdiffstats
path: root/deluge/ui
diff options
context:
space:
mode:
Diffstat (limited to 'deluge/ui')
-rw-r--r--deluge/ui/gtkui/common.py52
-rw-r--r--deluge/ui/gtkui/files_tab.py34
-rw-r--r--deluge/ui/gtkui/gtkui.py20
-rw-r--r--deluge/ui/gtkui/listview.py35
-rw-r--r--deluge/ui/gtkui/peers_tab.py29
-rw-r--r--deluge/ui/gtkui/torrentdetails.py34
6 files changed, 80 insertions, 124 deletions
diff --git a/deluge/ui/gtkui/common.py b/deluge/ui/gtkui/common.py
index 088223803..1c31453ba 100644
--- a/deluge/ui/gtkui/common.py
+++ b/deluge/ui/gtkui/common.py
@@ -41,6 +41,8 @@ import pygtk
pygtk.require('2.0')
import gtk
import logging
+import cPickle
+import shutil
import deluge.component as component
import deluge.common
@@ -264,3 +266,53 @@ def associate_magnet_links(overwrite=False):
log.error("Unable to register Deluge as default magnet uri handler.")
return False
return False
+
+def save_pickled_state_file(filename, state):
+ """Save a file in the config directory and creates a backup
+ filename: Filename to be saved to config
+ state: The data to be pickled and written to file
+ """
+ from deluge.configmanager import get_config_dir
+ filepath = os.path.join(get_config_dir(), "gtkui_state", filename)
+ filepath_bak = filepath + ".bak"
+
+ try:
+ if os.path.isfile(filepath):
+ log.info("Creating backup of %s at: %s", filename, filepath_bak)
+ shutil.copy2(filepath, filepath_bak)
+ except IOError as ex:
+ log.error("Unable to backup %s to %s: %s", filepath, filepath_bak, ex)
+ else:
+ log.info("Saving the %s at: %s", filename, filepath)
+ try:
+ with open(filepath, "wb") as _file:
+ # Pickle the state object
+ cPickle.dump(state, _file)
+ _file.flush()
+ os.fsync(_file.fileno())
+ except (IOError, EOFError, cPickle.PicklingError) as ex:
+ log.error("Unable to save %s: %s", filename, ex)
+ if os.path.isfile(filepath_bak):
+ log.info("Restoring backup of %s from: %s", filename, filepath_bak)
+ shutil.move(filepath_bak, filepath)
+
+def load_pickled_state_file(filename):
+ """Loads a file from the config directory, attempting backup if original fails to load.
+ filename: Filename to be loaded from config
+ returns unpickled state
+ """
+ from deluge.configmanager import get_config_dir
+ filepath = os.path.join(get_config_dir(), "gtkui_state", filename)
+ filepath_bak = filepath + ".bak"
+ old_data_filepath = os.path.join(get_config_dir(), filename)
+
+ for _filepath in (filepath, filepath_bak, old_data_filepath):
+ log.info("Opening %s for load: %s", filename, _filepath)
+ try:
+ with open(_filepath, "rb") as _file:
+ state = cPickle.load(_file)
+ except (IOError, cPickle.UnpicklingError), ex:
+ log.warning("Unable to load %s: %s", _filepath, ex)
+ else:
+ log.info("Successfully loaded %s: %s", filename, _filepath)
+ return state
diff --git a/deluge/ui/gtkui/files_tab.py b/deluge/ui/gtkui/files_tab.py
index 82f8ec573..5fa36c48a 100644
--- a/deluge/ui/gtkui/files_tab.py
+++ b/deluge/ui/gtkui/files_tab.py
@@ -38,15 +38,14 @@ import gtk
import gtk.gdk
import gobject
import os.path
-import cPickle
import logging
+import cPickle
from deluge.ui.gtkui.torrentdetails import Tab
from deluge.ui.client import client
-import deluge.configmanager
import deluge.component as component
import deluge.common
-import common
+from deluge.ui.gtkui.common import reparent_iter, save_pickled_state_file, load_pickled_state_file
log = logging.getLogger(__name__)
@@ -242,7 +241,6 @@ class FilesTab(Tab):
getattr(widget, attr)()
def save_state(self):
- filename = "files_tab.state"
# Get the current sort order of the view
column_id, sort_order = self.treestore.get_sort_column_id()
@@ -259,30 +257,10 @@ class FilesTab(Tab):
"width": column.get_width()
}
- # Get the config location for saving the state file
- config_location = deluge.configmanager.get_config_dir()
-
- try:
- log.debug("Saving FilesTab state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "wb")
- cPickle.dump(state, state_file)
- state_file.close()
- except IOError, e:
- log.warning("Unable to save state file: %s", e)
+ save_pickled_state_file("files_tab.state", state)
def load_state(self):
- filename = "files_tab.state"
- # Get the config location for loading the state file
- config_location = deluge.configmanager.get_config_dir()
- state = None
-
- try:
- log.debug("Loading FilesTab state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "rb")
- state = cPickle.load(state_file)
- state_file.close()
- except (EOFError, IOError, AttributeError, cPickle.UnpicklingError), e:
- log.warning("Unable to load state file: %s", e)
+ state = load_pickled_state_file("files_tabs.state")
if state == None:
return
@@ -807,14 +785,14 @@ class FilesTab(Tab):
return
if new_folder_iter:
# This means that a folder by this name already exists
- common.reparent_iter(self.treestore, self.treestore.iter_children(old_folder_iter), new_folder_iter)
+ reparent_iter(self.treestore, self.treestore.iter_children(old_folder_iter), new_folder_iter)
else:
parent = old_folder_iter_parent
for ns in new_split[:-1]:
parent = self.treestore.append(parent, [ns + "/", 0, "", 0, 0, -1, gtk.STOCK_DIRECTORY])
self.treestore[old_folder_iter][0] = new_split[-1] + "/"
- common.reparent_iter(self.treestore, old_folder_iter, parent)
+ reparent_iter(self.treestore, old_folder_iter, parent)
# We need to check if the old_folder_iter_parent no longer has children
# and if so, we delete it
diff --git a/deluge/ui/gtkui/gtkui.py b/deluge/ui/gtkui/gtkui.py
index 28b892d58..f4ed2be9f 100644
--- a/deluge/ui/gtkui/gtkui.py
+++ b/deluge/ui/gtkui/gtkui.py
@@ -40,6 +40,7 @@ gobject.set_prgname("deluge")
from twisted.internet import gtk2reactor
reactor = gtk2reactor.install()
+import os
import gtk
import sys
import logging
@@ -71,14 +72,13 @@ from queuedtorrents import QueuedTorrents
from addtorrentdialog import AddTorrentDialog
from deluge.ui.sessionproxy import SessionProxy
import dialogs
-import common
-
-import deluge.configmanager
+from deluge.ui.gtkui.common import associate_magnet_links
+from deluge.configmanager import ConfigManager, get_config_dir
import deluge.common
import deluge.error
-
from deluge.ui.ui import _UI
+
class Gtk(_UI):
help = """Starts the Deluge GTK+ interface"""
@@ -90,6 +90,7 @@ class Gtk(_UI):
super(Gtk, self).start()
GtkUI(self.args)
+
def start():
Gtk().start()
@@ -152,6 +153,7 @@ DEFAULT_PREFS = {
"focus_main_window_on_add": True,
}
+
class GtkUI(object):
def __init__(self, args):
self.daemon_bps = (0,0,0)
@@ -192,10 +194,14 @@ class GtkUI(object):
# Attempt to register a magnet URI handler with gconf, but do not overwrite
# if already set by another program.
- common.associate_magnet_links(False)
+ associate_magnet_links(False)
# Make sure gtkui.conf has at least the defaults set
- self.config = deluge.configmanager.ConfigManager("gtkui.conf", DEFAULT_PREFS)
+ self.config = ConfigManager("gtkui.conf", DEFAULT_PREFS)
+
+ # Make sure the gtkui state folder has been created
+ if not os.path.exists(os.path.join(get_config_dir(), "gtkui_state")):
+ os.makedirs(os.path.join(get_config_dir(), "gtkui_state"))
# We need to check on exit if it was started in classic mode to ensure we
# shutdown the daemon.
@@ -370,7 +376,7 @@ Please see the details below for more information."), details=traceback.format_e
if self.config["autostart_localhost"] and host in ("localhost", "127.0.0.1"):
log.debug("Autostarting localhost:%s", host)
try_connect = client.start_daemon(
- port, deluge.configmanager.get_config_dir()
+ port, get_config_dir()
)
log.debug("Localhost started: %s", try_connect)
if not try_connect:
diff --git a/deluge/ui/gtkui/listview.py b/deluge/ui/gtkui/listview.py
index 07af28b7e..07f45d1a6 100644
--- a/deluge/ui/gtkui/listview.py
+++ b/deluge/ui/gtkui/listview.py
@@ -34,19 +34,13 @@
#
#
-
-import cPickle
-import os.path
import logging
-
import pygtk
pygtk.require('2.0')
import gtk
-import gettext
-from deluge.configmanager import ConfigManager
-import deluge.configmanager
import deluge.common
+from deluge.ui.gtkui.common import save_pickled_state_file, load_pickled_state_file
from gobject import signal_new, SIGNAL_RUN_LAST, TYPE_NONE
from gtk import gdk
@@ -333,34 +327,11 @@ class ListView:
state.append(self.create_column_state(column, counter))
state += self.removed_columns_state
-
- # Get the config location for saving the state file
- config_location = deluge.configmanager.get_config_dir()
-
- try:
- log.debug("Saving ListView state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "wb")
- cPickle.dump(state, state_file)
- state_file.close()
- except IOError, e:
- log.warning("Unable to save state file: %s", e)
+ save_pickled_state_file(filename, state)
def load_state(self, filename):
"""Load the listview state from filename."""
- # Get the config location for loading the state file
- config_location = deluge.configmanager.get_config_dir()
- state = None
-
- try:
- log.debug("Loading ListView state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "rb")
- state = cPickle.load(state_file)
- state_file.close()
- except (EOFError, IOError, cPickle.UnpicklingError), e:
- log.warning("Unable to load state file: %s", e)
-
- # Keep the state in self.state so we can access it as we add new columns
- self.state = state
+ self.state = load_pickled_state_file(filename)
def set_treeview(self, treeview_widget):
"""Set the treeview widget that this listview uses."""
diff --git a/deluge/ui/gtkui/peers_tab.py b/deluge/ui/gtkui/peers_tab.py
index e3adde3ac..5efbaa385 100644
--- a/deluge/ui/gtkui/peers_tab.py
+++ b/deluge/ui/gtkui/peers_tab.py
@@ -36,16 +36,15 @@
import gtk
import logging
import os.path
-import cPickle
from itertools import izip
from deluge.ui.client import client
-import deluge.configmanager
import deluge.component as component
import deluge.common
from deluge.ui.gtkui.listview import cell_data_speed as cell_data_speed
from deluge.ui.gtkui.torrentdetails import Tab
from deluge.ui.countries import COUNTRIES
+from deluge.ui.gtkui.common import save_pickled_state_file, load_pickled_state_file
log = logging.getLogger(__name__)
@@ -171,7 +170,6 @@ class PeersTab(Tab):
self.torrent_id = None
def save_state(self):
- filename = "peers_tab.state"
# Get the current sort order of the view
column_id, sort_order = self.liststore.get_sort_column_id()
@@ -187,31 +185,10 @@ class PeersTab(Tab):
"position": index,
"width": column.get_width()
}
-
- # Get the config location for saving the state file
- config_location = deluge.configmanager.get_config_dir()
-
- try:
- log.debug("Saving FilesTab state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "wb")
- cPickle.dump(state, state_file)
- state_file.close()
- except IOError, e:
- log.warning("Unable to save state file: %s", e)
+ save_pickled_state_file("peers_tab.state", state)
def load_state(self):
- filename = "peers_tab.state"
- # Get the config location for loading the state file
- config_location = deluge.configmanager.get_config_dir()
- state = None
-
- try:
- log.debug("Loading PeersTab state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "rb")
- state = cPickle.load(state_file)
- state_file.close()
- except (EOFError, IOError, AttributeError, cPickle.UnpicklingError), e:
- log.warning("Unable to load state file: %s", e)
+ state = load_pickled_state_file("peers_tabs.state")
if state == None:
return
diff --git a/deluge/ui/gtkui/torrentdetails.py b/deluge/ui/gtkui/torrentdetails.py
index 2d836c6eb..3de609dd7 100644
--- a/deluge/ui/gtkui/torrentdetails.py
+++ b/deluge/ui/gtkui/torrentdetails.py
@@ -37,15 +37,11 @@
"""The torrent details component shows info about the selected torrent."""
import gtk
-import os
-import os.path
-import cPickle
import logging
import deluge.component as component
from deluge.ui.client import client
-from deluge.configmanager import ConfigManager
-import deluge.configmanager
+from deluge.ui.gtkui.common import save_pickled_state_file, load_pickled_state_file
log = logging.getLogger(__name__)
@@ -411,8 +407,6 @@ class TorrentDetails(component.Component):
def save_state(self):
"""We save the state, which is basically the tab_index list"""
- filename = "tabs.state"
-
#Update the visiblity status of all tabs
#Leave tabs we dont know anything about it the state as they
#might come from a plugin
@@ -423,29 +417,7 @@ class TorrentDetails(component.Component):
log.debug("Set to %s %d" % self.state[i])
state = self.state
- # Get the config location for saving the state file
- config_location = deluge.configmanager.get_config_dir()
-
- try:
- log.debug("Saving TorrentDetails state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "wb")
- cPickle.dump(state, state_file)
- state_file.close()
- except IOError, e:
- log.warning("Unable to save state file: %s", e)
+ save_pickled_state_file("tabs.state", state)
def load_state(self):
- filename = "tabs.state"
- # Get the config location for loading the state file
- config_location = deluge.configmanager.get_config_dir()
- state = None
-
- try:
- log.debug("Loading TorrentDetails state file: %s", filename)
- state_file = open(os.path.join(config_location, filename), "rb")
- state = cPickle.load(state_file)
- state_file.close()
- except (EOFError, IOError, cPickle.UnpicklingError), e:
- log.warning("Unable to load state file: %s", e)
-
- return state
+ return load_pickled_state_file("tabs.state")