mirror of
https://github.com/transmission/transmission.git
synced 2025-12-19 18:08:31 +00:00
Fails with an error if data removal was not possible (#6055)
* Do not remove torrent if trashing files failed. Instead, stop the torrent and sets an error. * Fixing GTK interface with new file removal behavior. * C++17 compliant. * Reverting unrelated change. * Avoiding allocating unecessary objects. * Easy review fixes. * Fixing merge error. * Adding result callback to tr_torrentRemove(). Using the new callback in Gtk GUI to decide when to remove it from the interface. * Reducing indentation level and making the function more readable. * Using existing Session RefPtr. * Notifying the client before freeing the torrent in the session. * Addressing comments and synchronizing callback. * Moving include. * Fix constness issue reported by clang-tidy
This commit is contained in:
committed by
GitHub
parent
abfd39065c
commit
9fc9daf40d
@@ -32,6 +32,7 @@
|
||||
#include <glibmm/i18n.h>
|
||||
#include <glibmm/main.h>
|
||||
#include <glibmm/miscutils.h>
|
||||
#include <glibmm/refptr.h>
|
||||
#include <glibmm/stringutils.h>
|
||||
#include <glibmm/variant.h>
|
||||
|
||||
@@ -51,6 +52,7 @@
|
||||
#include <iostream>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <mutex>
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <string_view>
|
||||
@@ -87,6 +89,8 @@ public:
|
||||
void add_torrent(Glib::RefPtr<Torrent> const& torrent, bool do_notify);
|
||||
bool add_from_url(Glib::ustring const& url);
|
||||
|
||||
void remove_torrent(tr_torrent_id_t id, bool delete_files);
|
||||
|
||||
void send_rpc_request(tr_variant const& request, int64_t tag, std::function<void(tr_variant&)> const& response_func);
|
||||
|
||||
void commit_prefs_change(tr_quark key);
|
||||
@@ -905,10 +909,51 @@ void Session::torrent_changed(tr_torrent_id_t id)
|
||||
|
||||
void Session::remove_torrent(tr_torrent_id_t id, bool delete_files)
|
||||
{
|
||||
if (auto const& [torrent, position] = impl_->find_torrent_by_id(id); torrent)
|
||||
impl_->remove_torrent(id, delete_files);
|
||||
}
|
||||
|
||||
void Session::Impl::remove_torrent(tr_torrent_id_t id, bool delete_files)
|
||||
{
|
||||
if (auto const& [torrent, position] = find_torrent_by_id(id); torrent)
|
||||
{
|
||||
/* remove from the gui */
|
||||
impl_->get_raw_model()->remove(position);
|
||||
struct CallbackUserData
|
||||
{
|
||||
Glib::RefPtr<Session> session;
|
||||
tr_torrent_id_t id;
|
||||
};
|
||||
|
||||
// Callback to remove the torrent entry from the GUI if it was
|
||||
// successfuly removed. This is called from the libtransmission thread.
|
||||
auto handle_result = [](bool succeeded, void* user_data)
|
||||
{
|
||||
std::mutex wait_cb_thread;
|
||||
wait_cb_thread.lock();
|
||||
|
||||
// Schedule the actual handler in the main thread:
|
||||
Glib::signal_idle().connect_once(
|
||||
[=, &wait_cb_thread]()
|
||||
{
|
||||
// Take ownership of the raw pointer, so it gets deleted when done.
|
||||
auto ud = std::unique_ptr<CallbackUserData>(static_cast<CallbackUserData*>(user_data));
|
||||
|
||||
if (succeeded)
|
||||
{
|
||||
auto const& impl = *ud->session->impl_;
|
||||
if (auto const& [torrent_, position_] = impl.find_torrent_by_id(ud->id); torrent_)
|
||||
{
|
||||
/* remove from the gui */
|
||||
impl.get_raw_model()->remove(position_);
|
||||
}
|
||||
}
|
||||
|
||||
wait_cb_thread.unlock();
|
||||
});
|
||||
|
||||
// It is better to wait for the idle signal to be processed before
|
||||
// returning, just to avoid the extremely improbable case of the
|
||||
// tr_torrent_id_t being reused before the idle signal is processed.
|
||||
std::lock_guard waiter{ wait_cb_thread };
|
||||
};
|
||||
|
||||
/* remove the torrent */
|
||||
tr_torrentRemove(
|
||||
@@ -916,7 +961,9 @@ void Session::remove_torrent(tr_torrent_id_t id, bool delete_files)
|
||||
delete_files,
|
||||
[](char const* filename, void* /*user_data*/, tr_error* error)
|
||||
{ return gtr_file_trash_or_remove(filename, error); },
|
||||
nullptr);
|
||||
nullptr,
|
||||
handle_result,
|
||||
new CallbackUserData{ get_core_ptr(), id });
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user