Browse Source

Merge pull request #4482 from glassez/savepath

Manage save path in one place
adaptive-webui-19844
sledgehammer999 9 years ago
parent
commit
4a5f29b0d1
  1. 40
      src/base/bittorrent/magneturi.cpp
  2. 2
      src/base/bittorrent/magneturi.h
  3. 141
      src/base/bittorrent/session.cpp
  4. 14
      src/base/bittorrent/session.h
  5. 40
      src/base/bittorrent/torrenthandle.cpp
  6. 8
      src/base/bittorrent/torrenthandle.h
  7. 15
      src/base/utils/misc.cpp
  8. 1
      src/base/utils/misc.h
  9. 39
      src/gui/addnewtorrentdialog.cpp
  10. 14
      src/gui/addnewtorrentdialog.h
  11. 8
      src/webui/webapplication.cpp

40
src/base/bittorrent/magneturi.cpp

@ -26,6 +26,10 @@
* exception statement from your version. * exception statement from your version.
*/ */
#include <QByteArray>
#include <QRegExp>
#include <QStringList>
#include <libtorrent/bencode.hpp> #include <libtorrent/bencode.hpp>
#include <libtorrent/error_code.hpp> #include <libtorrent/error_code.hpp>
#include <libtorrent/magnet_uri.hpp> #include <libtorrent/magnet_uri.hpp>
@ -33,17 +37,45 @@
#include "base/utils/string.h" #include "base/utils/string.h"
#include "magneturi.h" #include "magneturi.h"
namespace
{
QString bcLinkToMagnet(QString bcLink)
{
QByteArray rawBc = bcLink.toUtf8();
rawBc = rawBc.mid(8); // skip bc://bt/
rawBc = QByteArray::fromBase64(rawBc); // Decode base64
// Format is now AA/url_encoded_filename/size_bytes/info_hash/ZZ
QStringList parts = QString(rawBc).split("/");
if (parts.size() != 5) return QString();
QString filename = parts.at(1);
QString hash = parts.at(3);
QString magnet = "magnet:?xt=urn:btih:" + hash;
magnet += "&dn=" + filename;
return magnet;
}
}
namespace libt = libtorrent; namespace libt = libtorrent;
using namespace BitTorrent; using namespace BitTorrent;
MagnetUri::MagnetUri(const QString &url) MagnetUri::MagnetUri(const QString &source)
: m_valid(false) : m_valid(false)
, m_url(url) , m_url(source)
{ {
if (url.isEmpty()) return; if (source.isEmpty()) return;
if (source.startsWith("bc://bt/", Qt::CaseInsensitive)) {
qDebug("Creating magnet link from bc link");
m_url = bcLinkToMagnet(source);
}
else if (((source.size() == 40) && !source.contains(QRegExp("[^0-9A-Fa-f]")))
|| ((source.size() == 32) && !source.contains(QRegExp("[^2-7A-Za-z]")))) {
m_url = "magnet:?xt=urn:btih:" + source;
}
libt::error_code ec; libt::error_code ec;
libt::parse_magnet_uri(url.toUtf8().constData(), m_addTorrentParams, ec); libt::parse_magnet_uri(m_url.toUtf8().constData(), m_addTorrentParams, ec);
if (ec) return; if (ec) return;
m_valid = true; m_valid = true;

2
src/base/bittorrent/magneturi.h

@ -43,7 +43,7 @@ namespace BitTorrent
class MagnetUri class MagnetUri
{ {
public: public:
explicit MagnetUri(const QString &url = QString()); explicit MagnetUri(const QString &source = QString());
bool isValid() const; bool isValid() const;
InfoHash hash() const; InfoHash hash() const;

141
src/base/bittorrent/session.cpp

@ -100,16 +100,6 @@ static void torrentQueuePositionDown(const libt::torrent_handle &handle);
static void torrentQueuePositionTop(const libt::torrent_handle &handle); static void torrentQueuePositionTop(const libt::torrent_handle &handle);
static void torrentQueuePositionBottom(const libt::torrent_handle &handle); static void torrentQueuePositionBottom(const libt::torrent_handle &handle);
// AddTorrentParams
AddTorrentParams::AddTorrentParams()
: disableTempPath(false)
, sequential(false)
, ignoreShareRatio(false)
, skipChecking(false)
{
}
// Session // Session
Session *Session::m_instance = 0; Session *Session::m_instance = 0;
@ -713,7 +703,7 @@ void Session::handleDownloadFailed(const QString &url, const QString &reason)
void Session::handleRedirectedToMagnet(const QString &url, const QString &magnetUri) void Session::handleRedirectedToMagnet(const QString &url, const QString &magnetUri)
{ {
addTorrent_impl(addDataFromParams(m_downloadedTorrents.take(url)), MagnetUri(magnetUri)); addTorrent_impl(m_downloadedTorrents.take(url), MagnetUri(magnetUri));
} }
void Session::switchToAlternativeMode(bool alternative) void Session::switchToAlternativeMode(bool alternative)
@ -725,7 +715,7 @@ void Session::switchToAlternativeMode(bool alternative)
void Session::handleDownloadFinished(const QString &url, const QString &filePath) void Session::handleDownloadFinished(const QString &url, const QString &filePath)
{ {
emit downloadFromUrlFinished(url); emit downloadFromUrlFinished(url);
addTorrent_impl(addDataFromParams(m_downloadedTorrents.take(url)), MagnetUri(), TorrentInfo::loadFromFile(filePath)); addTorrent_impl(m_downloadedTorrents.take(url), MagnetUri(), TorrentInfo::loadFromFile(filePath));
Utils::Fs::forceRemove(filePath); // remove temporary file Utils::Fs::forceRemove(filePath); // remove temporary file
} }
@ -939,40 +929,14 @@ TorrentStatusReport Session::torrentStatusReport() const
return m_torrentStatusReport; return m_torrentStatusReport;
} }
// source - .torrent file path/url or magnet uri (hash for preloaded torrent) // source - .torrent file path/url or magnet uri
bool Session::addTorrent(QString source, const AddTorrentParams &params) bool Session::addTorrent(QString source, const AddTorrentParams &params)
{ {
InfoHash hash = source; MagnetUri magnetUri(source);
if (hash.isValid() && m_loadedMetadata.contains(hash)) { if (magnetUri.isValid()) {
// Adding preloaded torrent return addTorrent_impl(params, magnetUri);
m_loadedMetadata.remove(hash);
libt::torrent_handle handle = m_nativeSession->find_torrent(hash);
--m_extraLimit;
try {
handle.auto_managed(false);
handle.pause();
}
catch (std::exception &) {}
adjustLimits();
// use common 2nd step of torrent addition
m_addingTorrents.insert(hash, addDataFromParams(params));
createTorrentHandle(handle);
return true;
}
if (source.startsWith("bc://bt/", Qt::CaseInsensitive)) {
qDebug("Converting bc link to magnet link");
source = Utils::Misc::bcLinkToMagnet(source);
} }
else if (((source.size() == 40) && !source.contains(QRegExp("[^0-9A-Fa-f]"))) else if (Utils::Misc::isUrl(source)) {
|| ((source.size() == 32) && !source.contains(QRegExp("[^2-7A-Za-z]")))) {
source = "magnet:?xt=urn:btih:" + source;
}
if (Utils::Misc::isUrl(source)) {
Logger::instance()->addMessage(tr("Downloading '%1', please wait...", "e.g: Downloading 'xxx.torrent', please wait...").arg(source)); Logger::instance()->addMessage(tr("Downloading '%1', please wait...", "e.g: Downloading 'xxx.torrent', please wait...").arg(source));
// Launch downloader // Launch downloader
Net::DownloadHandler *handler = Net::DownloadManager::instance()->downloadUrl(source, true, 10485760 /* 10MB */, true); Net::DownloadHandler *handler = Net::DownloadManager::instance()->downloadUrl(source, true, 10485760 /* 10MB */, true);
@ -981,11 +945,8 @@ bool Session::addTorrent(QString source, const AddTorrentParams &params)
connect(handler, SIGNAL(redirectedToMagnet(QString, QString)), this, SLOT(handleRedirectedToMagnet(QString, QString))); connect(handler, SIGNAL(redirectedToMagnet(QString, QString)), this, SLOT(handleRedirectedToMagnet(QString, QString)));
m_downloadedTorrents[handler->url()] = params; m_downloadedTorrents[handler->url()] = params;
} }
else if (source.startsWith("magnet:", Qt::CaseInsensitive)) {
return addTorrent_impl(addDataFromParams(params), MagnetUri(source));
}
else { else {
return addTorrent_impl(addDataFromParams(params), MagnetUri(), TorrentInfo::loadFromFile(source)); return addTorrent_impl(params, MagnetUri(), TorrentInfo::loadFromFile(source));
} }
return false; return false;
@ -995,13 +956,26 @@ bool Session::addTorrent(const TorrentInfo &torrentInfo, const AddTorrentParams
{ {
if (!torrentInfo.isValid()) return false; if (!torrentInfo.isValid()) return false;
return addTorrent_impl(addDataFromParams(params), MagnetUri(), torrentInfo); return addTorrent_impl(params, MagnetUri(), torrentInfo);
} }
// Add a torrent to the BitTorrent session // Add a torrent to the BitTorrent session
bool Session::addTorrent_impl(AddTorrentData addData, const MagnetUri &magnetUri, bool Session::addTorrent_impl(AddTorrentData addData, const MagnetUri &magnetUri,
const TorrentInfo &torrentInfo, const QByteArray &fastresumeData) const TorrentInfo &torrentInfo, const QByteArray &fastresumeData)
{ {
if (!addData.resumed) {
// manage save path
QString defaultSavePath = this->defaultSavePath();
if (addData.savePath.isEmpty())
addData.savePath = defaultSavePath;
if (!addData.savePath.endsWith("/"))
addData.savePath += "/";
if (useAppendLabelToSavePath()) {
if ((addData.savePath == defaultSavePath) && !addData.label.isEmpty())
addData.savePath += QString("%1/").arg(addData.label);
}
}
libt::add_torrent_params p; libt::add_torrent_params p;
InfoHash hash; InfoHash hash;
std::vector<char> buf(fastresumeData.constData(), fastresumeData.constData() + fastresumeData.size()); std::vector<char> buf(fastresumeData.constData(), fastresumeData.constData() + fastresumeData.size());
@ -1009,8 +983,29 @@ bool Session::addTorrent_impl(AddTorrentData addData, const MagnetUri &magnetUri
bool fromMagnetUri = magnetUri.isValid(); bool fromMagnetUri = magnetUri.isValid();
if (fromMagnetUri) { if (fromMagnetUri) {
p = magnetUri.addTorrentParams();
hash = magnetUri.hash(); hash = magnetUri.hash();
if (m_loadedMetadata.contains(hash)) {
// Adding preloaded torrent
m_loadedMetadata.remove(hash);
libt::torrent_handle handle = m_nativeSession->find_torrent(hash);
--m_extraLimit;
try {
handle.auto_managed(false);
handle.pause();
}
catch (std::exception &) {}
adjustLimits();
// use common 2nd step of torrent addition
m_addingTorrents.insert(hash, addData);
createTorrentHandle(handle);
return true;
}
p = magnetUri.addTorrentParams();
} }
else if (torrentInfo.isValid()) { else if (torrentInfo.isValid()) {
// Metadata // Metadata
@ -1091,15 +1086,12 @@ bool Session::addTorrent_impl(AddTorrentData addData, const MagnetUri &magnetUri
// Add a torrent to the BitTorrent session in hidden mode // Add a torrent to the BitTorrent session in hidden mode
// and force it to load its metadata // and force it to load its metadata
bool Session::loadMetadata(const QString &magnetUri) bool Session::loadMetadata(const MagnetUri &magnetUri)
{ {
Q_ASSERT(magnetUri.startsWith("magnet:", Qt::CaseInsensitive)); if (!magnetUri.isValid()) return false;
MagnetUri magnet(magnetUri);
if (!magnet.isValid()) return false;
InfoHash hash = magnet.hash(); InfoHash hash = magnetUri.hash();
QString name = magnet.name(); QString name = magnetUri.name();
// We should not add torrent if it already // We should not add torrent if it already
// processed or adding to session // processed or adding to session
@ -1111,7 +1103,7 @@ bool Session::loadMetadata(const QString &magnetUri)
qDebug(" -> Hash: %s", qPrintable(hash)); qDebug(" -> Hash: %s", qPrintable(hash));
qDebug(" -> Name: %s", qPrintable(name)); qDebug(" -> Name: %s", qPrintable(name));
libt::add_torrent_params p = magnet.addTorrentParams(); libt::add_torrent_params p = magnetUri.addTorrentParams();
// Flags // Flags
// Preallocation mode // Preallocation mode
@ -2358,6 +2350,11 @@ bool loadTorrentResumeData(const QByteArray &data, AddTorrentData &out, MagnetUr
if (ec || (fast.type() != libt::lazy_entry::dict_t)) return false; if (ec || (fast.type() != libt::lazy_entry::dict_t)) return false;
out.savePath = Utils::Fs::fromNativePath(Utils::String::fromStdString(fast.dict_find_string_value("qBt-savePath"))); out.savePath = Utils::Fs::fromNativePath(Utils::String::fromStdString(fast.dict_find_string_value("qBt-savePath")));
if (out.savePath.isEmpty()) {
Logger::instance()->addMessage("Empty torrent save path was loaded from .fastresume file! Using default one...", Log::WARNING);
out.savePath = Preferences::instance()->getSavePath();
}
out.ratioLimit = Utils::String::fromStdString(fast.dict_find_string_value("qBt-ratioLimit")).toDouble(); out.ratioLimit = Utils::String::fromStdString(fast.dict_find_string_value("qBt-ratioLimit")).toDouble();
out.label = Utils::String::fromStdString(fast.dict_find_string_value("qBt-label")); out.label = Utils::String::fromStdString(fast.dict_find_string_value("qBt-label"));
out.name = Utils::String::fromStdString(fast.dict_find_string_value("qBt-name")); out.name = Utils::String::fromStdString(fast.dict_find_string_value("qBt-name"));
@ -2432,33 +2429,3 @@ void torrentQueuePositionBottom(const libt::torrent_handle &handle)
qDebug() << Q_FUNC_INFO << " fails: " << exc.what(); qDebug() << Q_FUNC_INFO << " fails: " << exc.what();
} }
} }
AddTorrentData Session::addDataFromParams(const AddTorrentParams &params)
{
AddTorrentData data;
data.resumed = false;
data.name = params.name;
data.label = params.label;
data.savePath = params.savePath;
data.disableTempPath = params.disableTempPath;
data.sequential = params.sequential;
data.hasSeedStatus = params.skipChecking; // do not react on 'torrent_finished_alert' when skipping
data.skipChecking = params.skipChecking;
data.addForced = params.addForced;
data.addPaused = params.addPaused;
data.filePriorities = params.filePriorities;
data.ratioLimit = params.ignoreShareRatio ? TorrentHandle::NO_RATIO_LIMIT : TorrentHandle::USE_GLOBAL_RATIO;
// normalize save path
if (data.savePath.isEmpty()) {
data.savePath = m_defaultSavePath;
if (m_appendLabelToSavePath && !data.label.isEmpty())
data.savePath += QString("%1/").arg(data.label);
}
else if (!data.savePath.endsWith("/")) {
data.savePath += "/";
}
return data;
}

14
src/base/bittorrent/session.h

@ -127,15 +127,13 @@ namespace BitTorrent
QString name; QString name;
QString label; QString label;
QString savePath; QString savePath;
bool disableTempPath; // e.g. for imported torrents bool disableTempPath = false; // e.g. for imported torrents
bool sequential; bool sequential = false;
TriStateBool addForced; TriStateBool addForced;
TriStateBool addPaused; TriStateBool addPaused;
QVector<int> filePriorities; // used if TorrentInfo is set QVector<int> filePriorities; // used if TorrentInfo is set
bool ignoreShareRatio; bool ignoreShareRatio = false;
bool skipChecking; bool skipChecking = false;
AddTorrentParams();
}; };
struct TorrentStatusReport struct TorrentStatusReport
@ -196,7 +194,7 @@ namespace BitTorrent
bool addTorrent(QString source, const AddTorrentParams &params = AddTorrentParams()); bool addTorrent(QString source, const AddTorrentParams &params = AddTorrentParams());
bool addTorrent(const TorrentInfo &torrentInfo, const AddTorrentParams &params = AddTorrentParams()); bool addTorrent(const TorrentInfo &torrentInfo, const AddTorrentParams &params = AddTorrentParams());
bool deleteTorrent(const QString &hash, bool deleteLocalFiles = false); bool deleteTorrent(const QString &hash, bool deleteLocalFiles = false);
bool loadMetadata(const QString &magnetUri); bool loadMetadata(const MagnetUri &magnetUri);
bool cancelLoadMetadata(const InfoHash &hash); bool cancelLoadMetadata(const InfoHash &hash);
void recursiveTorrentDownload(const InfoHash &hash); void recursiveTorrentDownload(const InfoHash &hash);
@ -334,8 +332,6 @@ namespace BitTorrent
void dispatchAlerts(std::auto_ptr<libtorrent::alert> alertPtr); void dispatchAlerts(std::auto_ptr<libtorrent::alert> alertPtr);
void getPendingAlerts(QVector<libtorrent::alert *> &out, ulong time = 0); void getPendingAlerts(QVector<libtorrent::alert *> &out, ulong time = 0);
AddTorrentData addDataFromParams(const AddTorrentParams &params);
// BitTorrent // BitTorrent
libtorrent::session *m_nativeSession; libtorrent::session *m_nativeSession;

40
src/base/bittorrent/torrenthandle.cpp

@ -65,10 +65,31 @@ static const char QB_EXT[] = ".!qB";
namespace libt = libtorrent; namespace libt = libtorrent;
using namespace BitTorrent; using namespace BitTorrent;
// TrackerInfo // AddTorrentData
TrackerInfo::TrackerInfo() AddTorrentData::AddTorrentData()
: numPeers(0) : resumed(false)
, disableTempPath(false)
, sequential(false)
, hasSeedStatus(false)
, skipChecking(false)
, ratioLimit(TorrentHandle::USE_GLOBAL_RATIO)
{
}
AddTorrentData::AddTorrentData(const AddTorrentParams &params)
: resumed(false)
, name(params.name)
, label(params.label)
, savePath(params.savePath)
, disableTempPath(params.disableTempPath)
, sequential(params.sequential)
, hasSeedStatus(params.skipChecking) // do not react on 'torrent_finished_alert' when skipping
, skipChecking(params.skipChecking)
, addForced(params.addForced)
, addPaused(params.addPaused)
, filePriorities(params.filePriorities)
, ratioLimit(params.ignoreShareRatio ? TorrentHandle::NO_RATIO_LIMIT : TorrentHandle::USE_GLOBAL_RATIO)
{ {
} }
@ -188,7 +209,11 @@ TorrentHandle::TorrentHandle(Session *session, const libtorrent::torrent_handle
, m_pauseAfterRecheck(false) , m_pauseAfterRecheck(false)
, m_needSaveResumeData(false) , m_needSaveResumeData(false)
{ {
initialize(); Q_ASSERT(!m_savePath.isEmpty());
updateStatus();
m_hash = InfoHash(m_nativeStatus.info_hash);
adjustActualSavePath();
if (!data.resumed) { if (!data.resumed) {
setSequentialDownload(data.sequential); setSequentialDownload(data.sequential);
@ -1704,13 +1729,6 @@ void TorrentHandle::updateTorrentInfo()
#endif #endif
} }
void TorrentHandle::initialize()
{
updateStatus();
m_hash = InfoHash(m_nativeStatus.info_hash);
adjustActualSavePath();
}
bool TorrentHandle::isMoveInProgress() const bool TorrentHandle::isMoveInProgress() const
{ {
return !m_newPath.isEmpty(); return !m_newPath.isEmpty();

8
src/base/bittorrent/torrenthandle.h

@ -102,14 +102,15 @@ namespace BitTorrent
QVector<int> filePriorities; QVector<int> filePriorities;
// for resumed torrents // for resumed torrents
qreal ratioLimit; qreal ratioLimit;
AddTorrentData();
AddTorrentData(const AddTorrentParams &params);
}; };
struct TrackerInfo struct TrackerInfo
{ {
QString lastMessage; QString lastMessage;
quint32 numPeers; quint32 numPeers = 0;
TrackerInfo();
}; };
class TorrentState class TorrentState
@ -349,7 +350,6 @@ namespace BitTorrent
private: private:
typedef boost::function<void ()> EventTrigger; typedef boost::function<void ()> EventTrigger;
void initialize();
void updateStatus(); void updateStatus();
void updateStatus(const libtorrent::torrent_status &nativeStatus); void updateStatus(const libtorrent::torrent_status &nativeStatus);
void updateState(); void updateState();

15
src/base/utils/misc.cpp

@ -392,21 +392,6 @@ bool Utils::Misc::isPreviewable(const QString& extension)
return multimedia_extensions.contains(extension.toUpper()); return multimedia_extensions.contains(extension.toUpper());
} }
QString Utils::Misc::bcLinkToMagnet(QString bc_link)
{
QByteArray raw_bc = bc_link.toUtf8();
raw_bc = raw_bc.mid(8); // skip bc://bt/
raw_bc = QByteArray::fromBase64(raw_bc); // Decode base64
// Format is now AA/url_encoded_filename/size_bytes/info_hash/ZZ
QStringList parts = QString(raw_bc).split("/");
if (parts.size() != 5) return QString::null;
QString filename = parts.at(1);
QString hash = parts.at(3);
QString magnet = "magnet:?xt=urn:btih:" + hash;
magnet += "&dn=" + filename;
return magnet;
}
// Take a number of seconds and return an user-friendly // Take a number of seconds and return an user-friendly
// time duration like "1d 2h 10m". // time duration like "1d 2h 10m".
QString Utils::Misc::userFriendlyDuration(qlonglong seconds) QString Utils::Misc::userFriendlyDuration(qlonglong seconds)

1
src/base/utils/misc.h

@ -66,7 +66,6 @@ namespace Utils
QString friendlyUnit(qreal val, bool is_speed = false); QString friendlyUnit(qreal val, bool is_speed = false);
bool isPreviewable(const QString& extension); bool isPreviewable(const QString& extension);
QString bcLinkToMagnet(QString bc_link);
// Take a number of seconds and return an user-friendly // Take a number of seconds and return an user-friendly
// time duration like "1d 2h 10m". // time duration like "1d 2h 10m".
QString userFriendlyDuration(qlonglong seconds); QString userFriendlyDuration(qlonglong seconds);

39
src/gui/addnewtorrentdialog.cpp

@ -133,15 +133,6 @@ void AddNewTorrentDialog::saveState()
void AddNewTorrentDialog::show(QString source, QWidget *parent) void AddNewTorrentDialog::show(QString source, QWidget *parent)
{ {
if (source.startsWith("bc://bt/", Qt::CaseInsensitive)) {
qDebug("Converting bc link to magnet link");
source = Utils::Misc::bcLinkToMagnet(source);
}
else if (((source.size() == 40) && !source.contains(QRegExp("[^0-9A-Fa-f]")))
|| ((source.size() == 32) && !source.contains(QRegExp("[^2-7A-Za-z]")))) {
source = "magnet:?xt=urn:btih:" + source;
}
AddNewTorrentDialog *dlg = new AddNewTorrentDialog(parent); AddNewTorrentDialog *dlg = new AddNewTorrentDialog(parent);
if (Utils::Misc::isUrl(source)) { if (Utils::Misc::isUrl(source)) {
@ -153,8 +144,9 @@ void AddNewTorrentDialog::show(QString source, QWidget *parent)
} }
else { else {
bool ok = false; bool ok = false;
if (source.startsWith("magnet:", Qt::CaseInsensitive)) BitTorrent::MagnetUri magnetUri(source);
ok = dlg->loadMagnet(source); if (magnetUri.isValid())
ok = dlg->loadMagnet(magnetUri);
else else
ok = dlg->loadTorrent(source); ok = dlg->loadTorrent(source);
@ -165,12 +157,12 @@ void AddNewTorrentDialog::show(QString source, QWidget *parent)
} }
} }
bool AddNewTorrentDialog::loadTorrent(const QString& torrent_path) bool AddNewTorrentDialog::loadTorrent(const QString &torrentPath)
{ {
if (torrent_path.startsWith("file://", Qt::CaseInsensitive)) if (torrentPath.startsWith("file://", Qt::CaseInsensitive))
m_filePath = QUrl::fromEncoded(torrent_path.toLocal8Bit()).toLocalFile(); m_filePath = QUrl::fromEncoded(torrentPath.toLocal8Bit()).toLocalFile();
else else
m_filePath = torrent_path; m_filePath = torrentPath;
if (!QFile::exists(m_filePath)) { if (!QFile::exists(m_filePath)) {
MessageBoxRaised::critical(0, tr("I/O Error"), tr("The torrent file does not exist.")); MessageBoxRaised::critical(0, tr("I/O Error"), tr("The torrent file does not exist."));
@ -212,21 +204,20 @@ bool AddNewTorrentDialog::loadTorrent(const QString& torrent_path)
return true; return true;
} }
bool AddNewTorrentDialog::loadMagnet(const QString &magnet_uri) bool AddNewTorrentDialog::loadMagnet(const BitTorrent::MagnetUri &magnetUri)
{ {
BitTorrent::MagnetUri magnet(magnet_uri); if (!magnetUri.isValid()) {
if (!magnet.isValid()) {
MessageBoxRaised::critical(0, tr("Invalid magnet link"), tr("This magnet link was not recognized")); MessageBoxRaised::critical(0, tr("Invalid magnet link"), tr("This magnet link was not recognized"));
return false; return false;
} }
m_hash = magnet.hash(); m_hash = magnetUri.hash();
// Prevent showing the dialog if download is already present // Prevent showing the dialog if download is already present
if (BitTorrent::Session::instance()->isKnownTorrent(m_hash)) { if (BitTorrent::Session::instance()->isKnownTorrent(m_hash)) {
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(m_hash); BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(m_hash);
if (torrent) { if (torrent) {
torrent->addTrackers(magnet.trackers()); torrent->addTrackers(magnetUri.trackers());
torrent->addUrlSeeds(magnet.urlSeeds()); torrent->addUrlSeeds(magnetUri.urlSeeds());
MessageBoxRaised::information(0, tr("Already in download list"), tr("Magnet link is already in download list. Trackers were merged."), QMessageBox::Ok); MessageBoxRaised::information(0, tr("Already in download list"), tr("Magnet link is already in download list. Trackers were merged."), QMessageBox::Ok);
} }
else { else {
@ -238,14 +229,14 @@ bool AddNewTorrentDialog::loadMagnet(const QString &magnet_uri)
connect(BitTorrent::Session::instance(), SIGNAL(metadataLoaded(BitTorrent::TorrentInfo)), SLOT(updateMetadata(BitTorrent::TorrentInfo))); connect(BitTorrent::Session::instance(), SIGNAL(metadataLoaded(BitTorrent::TorrentInfo)), SLOT(updateMetadata(BitTorrent::TorrentInfo)));
// Set dialog title // Set dialog title
QString torrent_name = magnet.name(); QString torrent_name = magnetUri.name();
setWindowTitle(torrent_name.isEmpty() ? tr("Magnet link") : torrent_name); setWindowTitle(torrent_name.isEmpty() ? tr("Magnet link") : torrent_name);
setupTreeview(); setupTreeview();
// Set dialog position // Set dialog position
setdialogPosition(); setdialogPosition();
BitTorrent::Session::instance()->loadMetadata(magnet_uri); BitTorrent::Session::instance()->loadMetadata(magnetUri);
setMetadataProgressIndicator(true, tr("Retrieving metadata...")); setMetadataProgressIndicator(true, tr("Retrieving metadata..."));
ui->lblhash->setText(m_hash); ui->lblhash->setText(m_hash);
@ -732,7 +723,7 @@ void AddNewTorrentDialog::handleDownloadFailed(const QString &url, const QString
void AddNewTorrentDialog::handleRedirectedToMagnet(const QString &url, const QString &magnetUri) void AddNewTorrentDialog::handleRedirectedToMagnet(const QString &url, const QString &magnetUri)
{ {
Q_UNUSED(url) Q_UNUSED(url)
if (loadMagnet(magnetUri)) if (loadMagnet(BitTorrent::MagnetUri(magnetUri)))
open(); open();
else else
this->deleteLater(); this->deleteLater();

14
src/gui/addnewtorrentdialog.h

@ -38,11 +38,15 @@
#include "base/bittorrent/infohash.h" #include "base/bittorrent/infohash.h"
#include "base/bittorrent/torrentinfo.h" #include "base/bittorrent/torrentinfo.h"
QT_BEGIN_NAMESPACE namespace BitTorrent
namespace Ui { {
class MagnetUri;
}
namespace Ui
{
class AddNewTorrentDialog; class AddNewTorrentDialog;
} }
QT_END_NAMESPACE
class TorrentContentFilterModel; class TorrentContentFilterModel;
class PropListDelegate; class PropListDelegate;
@ -79,8 +83,8 @@ protected slots:
private: private:
explicit AddNewTorrentDialog(QWidget *parent = 0); explicit AddNewTorrentDialog(QWidget *parent = 0);
bool loadTorrent(const QString& torrent_path); bool loadTorrent(const QString &torrentPath);
bool loadMagnet(const QString& magnet_uri); bool loadMagnet(const BitTorrent::MagnetUri &magnetUri);
void loadSavePathHistory(); void loadSavePathHistory();
void saveSavePathHistory() const; void saveSavePathHistory() const;
int indexOfSavePath(const QString& save_path); int indexOfSavePath(const QString& save_path);

8
src/webui/webapplication.cpp

@ -354,14 +354,6 @@ void WebApplication::action_command_download()
foreach (QString url, list) { foreach (QString url, list) {
url = url.trimmed(); url = url.trimmed();
if (!url.isEmpty()) { if (!url.isEmpty()) {
if (url.startsWith("bc://bt/", Qt::CaseInsensitive)) {
qDebug("Converting bc link to magnet link");
url = Utils::Misc::bcLinkToMagnet(url);
}
if ((url.size() == 40 && !url.contains(QRegExp("[^0-9A-Fa-f]")))
|| (url.size() == 32 && !url.contains(QRegExp("[^2-7A-Za-z]"))))
url = "magnet:?xt=urn:btih:" + url;
Net::DownloadManager::instance()->setCookiesFromUrl(cookies, QUrl::fromEncoded(url.toUtf8())); Net::DownloadManager::instance()->setCookiesFromUrl(cookies, QUrl::fromEncoded(url.toUtf8()));
BitTorrent::Session::instance()->addTorrent(url, params); BitTorrent::Session::instance()->addTorrent(url, params);
} }

Loading…
Cancel
Save