mirror of
https://git.deluge-torrent.org/deluge
synced 2025-08-11 02:48:39 +00:00
duplicate torrent trackers merge - micah
This commit is contained in:
parent
1f6d182f76
commit
e0311a9ff3
5 changed files with 176 additions and 47 deletions
56
glade/merge_dialog.glade
Normal file
56
glade/merge_dialog.glade
Normal file
|
@ -0,0 +1,56 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||||
|
<!DOCTYPE glade-interface SYSTEM "glade-2.0.dtd">
|
||||||
|
<!--*- mode: xml -*-->
|
||||||
|
<glade-interface>
|
||||||
|
<widget class="GtkDialog" id="merge_dialog">
|
||||||
|
<property name="border_width">5</property>
|
||||||
|
<property name="title" translatable="yes">Deluge Merge Tracker Lists</property>
|
||||||
|
<property name="window_position">GTK_WIN_POS_CENTER_ALWAYS</property>
|
||||||
|
<property name="default_width">200</property>
|
||||||
|
<property name="default_height">50</property>
|
||||||
|
<property name="has_separator">False</property>
|
||||||
|
<child internal-child="vbox">
|
||||||
|
<widget class="GtkVBox" id="dialog-vbox1">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK | GDK_ENTER_NOTIFY_MASK</property>
|
||||||
|
<property name="spacing">2</property>
|
||||||
|
<child>
|
||||||
|
<widget class="GtkLabel" id="label1">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="label" translatable="yes">Torrent already detected in Deluge, would you like to merge the tracker lists?</property>
|
||||||
|
</widget>
|
||||||
|
</child>
|
||||||
|
<child internal-child="action_area">
|
||||||
|
<widget class="GtkHButtonBox" id="dialog-action_area1">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK | GDK_ENTER_NOTIFY_MASK</property>
|
||||||
|
<property name="layout_style">GTK_BUTTONBOX_END</property>
|
||||||
|
<child>
|
||||||
|
<widget class="GtkButton" id="button_cancel">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="label" translatable="yes">gtk-cancel</property>
|
||||||
|
<property name="use_stock">True</property>
|
||||||
|
<property name="response_id">0</property>
|
||||||
|
</widget>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<widget class="GtkButton" id="button_ok">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="label" translatable="yes">gtk-ok</property>
|
||||||
|
<property name="use_stock">True</property>
|
||||||
|
<property name="response_id">1</property>
|
||||||
|
</widget>
|
||||||
|
<packing>
|
||||||
|
<property name="position">1</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
</widget>
|
||||||
|
<packing>
|
||||||
|
<property name="expand">False</property>
|
||||||
|
<property name="pack_type">GTK_PACK_END</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
</widget>
|
||||||
|
</child>
|
||||||
|
</widget>
|
||||||
|
</glade-interface>
|
|
@ -309,12 +309,20 @@ class Manager:
|
||||||
def dump_torrent_file_info(self, torrent):
|
def dump_torrent_file_info(self, torrent):
|
||||||
return deluge_core.dump_file_info(torrent)
|
return deluge_core.dump_file_info(torrent)
|
||||||
|
|
||||||
|
# Dump trackers from torrent file
|
||||||
|
def dump_trackers(self, torrent):
|
||||||
|
return deluge_core.dump_trackers(torrent)
|
||||||
|
|
||||||
# Torrent addition and removal functions
|
# Torrent addition and removal functions
|
||||||
|
|
||||||
def add_torrent(self, filename, save_dir, compact):
|
def add_torrent(self, filename, save_dir, compact):
|
||||||
self.add_torrent_ns(filename, save_dir, compact)
|
self.add_torrent_ns(filename, save_dir, compact)
|
||||||
return self.sync() # Syncing will create a new torrent in the core, and return it's ID
|
return self.sync() # Syncing will create a new torrent in the core, and return it's ID
|
||||||
|
|
||||||
|
# When duplicate torrent error, use to find duplicate when merging tracker lists
|
||||||
|
def test_duplicate(self, torrent, unique_id):
|
||||||
|
return deluge_core.test_duplicate(torrent, unique_id)
|
||||||
|
|
||||||
def remove_torrent(self, unique_ID, data_also, torrent_also):
|
def remove_torrent(self, unique_ID, data_also, torrent_also):
|
||||||
temp = self.unique_IDs[unique_ID]
|
temp = self.unique_IDs[unique_ID]
|
||||||
temp_fileinfo = deluge_core.get_file_info(unique_ID)
|
temp_fileinfo = deluge_core.get_file_info(unique_ID)
|
||||||
|
|
|
@ -170,7 +170,6 @@ long get_torrent_index(torrent_handle &handle)
|
||||||
RAISE_INT(DelugeError, "Handle not found.");
|
RAISE_INT(DelugeError, "Handle not found.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
long get_index_from_unique_ID(long unique_ID)
|
long get_index_from_unique_ID(long unique_ID)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
@ -181,7 +180,7 @@ long get_index_from_unique_ID(long unique_ID)
|
||||||
RAISE_INT(DelugeError, "No such unique_ID.");
|
RAISE_INT(DelugeError, "No such unique_ID.");
|
||||||
}
|
}
|
||||||
|
|
||||||
torrent_info internal_dump_file_info(std::string const& torrent_name)
|
torrent_info internal_get_torrent_info(std::string const& torrent_name)
|
||||||
{
|
{
|
||||||
std::ifstream in(torrent_name.c_str(), std::ios_base::binary);
|
std::ifstream in(torrent_name.c_str(), std::ios_base::binary);
|
||||||
in.unsetf(std::ios_base::skipws);
|
in.unsetf(std::ios_base::skipws);
|
||||||
|
@ -534,7 +533,7 @@ static PyObject *torrent_dump_file_info(PyObject *self, PyObject *args)
|
||||||
if (!PyArg_ParseTuple(args, "s", &name))
|
if (!PyArg_ParseTuple(args, "s", &name))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
torrent_info t = internal_dump_file_info(name);
|
torrent_info t = internal_get_torrent_info(name);
|
||||||
|
|
||||||
PyObject *file_info;
|
PyObject *file_info;
|
||||||
long file_index = 0;
|
long file_index = 0;
|
||||||
|
@ -557,6 +556,24 @@ static PyObject *torrent_dump_file_info(PyObject *self, PyObject *args)
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static PyObject *torrent_dump_trackers(PyObject *self, PyObject *args)
|
||||||
|
{
|
||||||
|
const char *name;
|
||||||
|
if (!PyArg_ParseTuple(args, "s", &name))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
torrent_info t = internal_get_torrent_info(name);
|
||||||
|
std::string trackerslist;
|
||||||
|
{
|
||||||
|
for (std::vector<announce_entry>::const_iterator i = t.trackers().begin();
|
||||||
|
i != t.trackers().end(); ++i)
|
||||||
|
{
|
||||||
|
trackerslist = trackerslist + i->url +"\n";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return Py_BuildValue("s",trackerslist.c_str());
|
||||||
|
}
|
||||||
|
|
||||||
static PyObject *torrent_add_torrent(PyObject *self, PyObject *args)
|
static PyObject *torrent_add_torrent(PyObject *self, PyObject *args)
|
||||||
{
|
{
|
||||||
const char *name, *save_dir;
|
const char *name, *save_dir;
|
||||||
|
@ -583,6 +600,22 @@ static PyObject *torrent_add_torrent(PyObject *self, PyObject *args)
|
||||||
{ RAISE_PTR(DuplicateTorrentError, "libtorrent reports this is a duplicate torrent"); }
|
{ RAISE_PTR(DuplicateTorrentError, "libtorrent reports this is a duplicate torrent"); }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static PyObject *torrent_test_duplicate(PyObject *self, PyObject *args)
|
||||||
|
{
|
||||||
|
const char *name;
|
||||||
|
python_long unique_ID;
|
||||||
|
if (!PyArg_ParseTuple(args, "si", &name, &unique_ID))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
long index = get_index_from_unique_ID(unique_ID);
|
||||||
|
if (PyErr_Occurred())
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
torrent_info t = internal_get_torrent_info(name);
|
||||||
|
return Py_BuildValue("b", t.info_hash() == M_torrents->at(index).handle.info_hash());
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
static PyObject *torrent_move_storage(PyObject *self, PyObject *args)
|
static PyObject *torrent_move_storage(PyObject *self, PyObject *args)
|
||||||
{
|
{
|
||||||
const char *move_dir;
|
const char *move_dir;
|
||||||
|
@ -1550,10 +1583,12 @@ static PyMethodDef deluge_core_methods[] =
|
||||||
{"set_ratio", torrent_set_ratio, METH_VARARGS, "."},
|
{"set_ratio", torrent_set_ratio, METH_VARARGS, "."},
|
||||||
{"proxy_settings", torrent_proxy_settings, METH_VARARGS, "."},
|
{"proxy_settings", torrent_proxy_settings, METH_VARARGS, "."},
|
||||||
{"get_trackers", torrent_get_trackers, METH_VARARGS, "."},
|
{"get_trackers", torrent_get_trackers, METH_VARARGS, "."},
|
||||||
|
{"dump_trackers", torrent_dump_trackers, METH_VARARGS, "."},
|
||||||
{"replace_trackers", torrent_replace_trackers, METH_VARARGS, "."},
|
{"replace_trackers", torrent_replace_trackers, METH_VARARGS, "."},
|
||||||
{"set_flp", torrent_set_flp, METH_VARARGS, "."},
|
{"set_flp", torrent_set_flp, METH_VARARGS, "."},
|
||||||
{"prioritize_files", torrent_prioritize_files, METH_VARARGS, "."},
|
{"prioritize_files", torrent_prioritize_files, METH_VARARGS, "."},
|
||||||
{"set_priv", torrent_set_priv, METH_VARARGS, "."},
|
{"set_priv", torrent_set_priv, METH_VARARGS, "."},
|
||||||
|
{"test_duplicate", torrent_test_duplicate, METH_VARARGS, "."},
|
||||||
{NULL}
|
{NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -201,6 +201,20 @@ class PreferencesDlg:
|
||||||
elif widget == self.glade.get_widget('chk_lock_tray'):
|
elif widget == self.glade.get_widget('chk_lock_tray'):
|
||||||
self.glade.get_widget('txt_tray_passwd').set_sensitive(value)
|
self.glade.get_widget('txt_tray_passwd').set_sensitive(value)
|
||||||
|
|
||||||
|
class MergeDlg:
|
||||||
|
def __init__(self):
|
||||||
|
self.glade = gtk.glade.XML(common.get_glade_file("merge_dialog.glade"),
|
||||||
|
domain='deluge')
|
||||||
|
self.dialog = self.glade.get_widget("merge_dialog")
|
||||||
|
self.dialog.set_icon_from_file(common.get_pixmap("deluge32.png"))
|
||||||
|
|
||||||
|
def show(self):
|
||||||
|
self.dialog.show()
|
||||||
|
r = self.dialog.run()
|
||||||
|
self.dialog.hide()
|
||||||
|
|
||||||
|
return r
|
||||||
|
|
||||||
class FilesDlg:
|
class FilesDlg:
|
||||||
def __init__(self, dumped_torrent):
|
def __init__(self, dumped_torrent):
|
||||||
self.glade = gtk.glade.XML(common.get_glade_file("files_dialog.glade"),
|
self.glade = gtk.glade.XML(common.get_glade_file("files_dialog.glade"),
|
||||||
|
|
|
@ -1108,7 +1108,23 @@ class DelugeGTK:
|
||||||
print "InvalidEncodingError", e
|
print "InvalidEncodingError", e
|
||||||
dialogs.show_popup_warning(self.window, _("An error occured while trying to add the torrent. It's possible your .torrent file is corrupted."))
|
dialogs.show_popup_warning(self.window, _("An error occured while trying to add the torrent. It's possible your .torrent file is corrupted."))
|
||||||
except core.DuplicateTorrentError, e:
|
except core.DuplicateTorrentError, e:
|
||||||
dialogs.show_popup_warning(self.window, _("The torrent you've added seems to already be in Deluge."))
|
for unique_id in self.manager.unique_IDs:
|
||||||
|
is_duplicate = self.manager.test_duplicate(torrent, unique_id)
|
||||||
|
if is_duplicate:
|
||||||
|
break
|
||||||
|
if is_duplicate:
|
||||||
|
merge_dialog = dialogs.MergeDlg()
|
||||||
|
if merge_dialog.show() == 1:
|
||||||
|
new_trackers_as_list = self.manager.dump_trackers(torrent).replace(' ','').splitlines(True)
|
||||||
|
original_trackers_as_list = self.manager.get_trackers(unique_id).replace(' ','').splitlines(True)
|
||||||
|
for index in xrange(len(new_trackers_as_list)):
|
||||||
|
if original_trackers_as_list.count(new_trackers_as_list[index]) == 0:
|
||||||
|
original_trackers_as_list.append(new_trackers_as_list[index])
|
||||||
|
merged_trackers_as_string = ''.join([original_trackers_as_list[index] for \
|
||||||
|
index in xrange(len(original_trackers_as_list))])
|
||||||
|
self.manager.replace_trackers(unique_id, merged_trackers_as_string)
|
||||||
|
else:
|
||||||
|
dialogs.show_popup_warning(self.window, _("Unknown duplicate torrent error."))
|
||||||
except core.InsufficientFreeSpaceError, e:
|
except core.InsufficientFreeSpaceError, e:
|
||||||
nice_need = common.fsize(e.needed_space)
|
nice_need = common.fsize(e.needed_space)
|
||||||
nice_free = common.fsize(e.free_space)
|
nice_free = common.fsize(e.free_space)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue