mirror of
https://github.com/d47081/qBittorrent.git
synced 2025-01-23 13:04:23 +00:00
Implement sync/torrent_peers request
This commit is contained in:
parent
aea6c38b33
commit
00c765be1b
@ -29,6 +29,7 @@
|
|||||||
#include "base/net/geoipmanager.h"
|
#include "base/net/geoipmanager.h"
|
||||||
#include "base/utils/string.h"
|
#include "base/utils/string.h"
|
||||||
#include "base/unicodestrings.h"
|
#include "base/unicodestrings.h"
|
||||||
|
#include "base/bittorrent/torrenthandle.h"
|
||||||
#include "peerinfo.h"
|
#include "peerinfo.h"
|
||||||
|
|
||||||
namespace libt = libtorrent;
|
namespace libt = libtorrent;
|
||||||
@ -49,9 +50,11 @@ PeerAddress::PeerAddress(QHostAddress ip, ushort port)
|
|||||||
|
|
||||||
// PeerInfo
|
// PeerInfo
|
||||||
|
|
||||||
PeerInfo::PeerInfo(const libt::peer_info &nativeInfo)
|
PeerInfo::PeerInfo(const TorrentHandle *torrent, const libt::peer_info &nativeInfo)
|
||||||
: m_nativeInfo(nativeInfo)
|
: m_nativeInfo(nativeInfo)
|
||||||
{
|
{
|
||||||
|
calcRelevance(torrent);
|
||||||
|
determineFlags();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PeerInfo::fromDHT() const
|
bool PeerInfo::fromDHT() const
|
||||||
@ -253,3 +256,155 @@ QString PeerInfo::connectionType() const
|
|||||||
|
|
||||||
return connection;
|
return connection;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void PeerInfo::calcRelevance(const TorrentHandle *torrent)
|
||||||
|
{
|
||||||
|
const QBitArray &allPieces = torrent->pieces();
|
||||||
|
const QBitArray &peerPieces = pieces();
|
||||||
|
|
||||||
|
int localMissing = 0;
|
||||||
|
int remoteHaves = 0;
|
||||||
|
|
||||||
|
for (int i = 0; i < allPieces.size(); ++i) {
|
||||||
|
if (!allPieces[i]) {
|
||||||
|
++localMissing;
|
||||||
|
if (peerPieces[i])
|
||||||
|
++remoteHaves;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (localMissing == 0)
|
||||||
|
m_relevance = 0.0;
|
||||||
|
else
|
||||||
|
m_relevance = static_cast<qreal>(remoteHaves) / localMissing;
|
||||||
|
}
|
||||||
|
|
||||||
|
qreal PeerInfo::relevance() const
|
||||||
|
{
|
||||||
|
return m_relevance;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PeerInfo::determineFlags()
|
||||||
|
{
|
||||||
|
if (isInteresting()) {
|
||||||
|
//d = Your client wants to download, but peer doesn't want to send (interested and choked)
|
||||||
|
if (isRemoteChocked()) {
|
||||||
|
m_flags += "d ";
|
||||||
|
m_flagsDescription += tr("interested(local) and choked(peer)");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
//D = Currently downloading (interested and not choked)
|
||||||
|
m_flags += "D ";
|
||||||
|
m_flagsDescription += tr("interested(local) and unchoked(peer)");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isRemoteInterested()) {
|
||||||
|
//u = Peer wants your client to upload, but your client doesn't want to (interested and choked)
|
||||||
|
if (isChocked()) {
|
||||||
|
m_flags += "u ";
|
||||||
|
m_flagsDescription += tr("interested(peer) and choked(local)");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
//U = Currently uploading (interested and not choked)
|
||||||
|
m_flags += "U ";
|
||||||
|
m_flagsDescription += tr("interested(peer) and unchoked(local)");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//O = Optimistic unchoke
|
||||||
|
if (optimisticUnchoke()) {
|
||||||
|
m_flags += "O ";
|
||||||
|
m_flagsDescription += tr("optimistic unchoke");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//S = Peer is snubbed
|
||||||
|
if (isSnubbed()) {
|
||||||
|
m_flags += "S ";
|
||||||
|
m_flagsDescription += tr("peer snubbed");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//I = Peer is an incoming connection
|
||||||
|
if (!isLocalConnection()) {
|
||||||
|
m_flags += "I ";
|
||||||
|
m_flagsDescription += tr("incoming connection");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//K = Peer is unchoking your client, but your client is not interested
|
||||||
|
if (!isRemoteChocked() && !isInteresting()) {
|
||||||
|
m_flags += "K ";
|
||||||
|
m_flagsDescription += tr("not interested(local) and unchoked(peer)");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//? = Your client unchoked the peer but the peer is not interested
|
||||||
|
if (!isChocked() && !isRemoteInterested()) {
|
||||||
|
m_flags += "? ";
|
||||||
|
m_flagsDescription += tr("not interested(peer) and unchoked(local)");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//X = Peer was included in peerlists obtained through Peer Exchange (PEX)
|
||||||
|
if (fromPeX()) {
|
||||||
|
m_flags += "X ";
|
||||||
|
m_flagsDescription += tr("peer from PEX");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//H = Peer was obtained through DHT
|
||||||
|
if (fromDHT()) {
|
||||||
|
m_flags += "H ";
|
||||||
|
m_flagsDescription += tr("peer from DHT");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//E = Peer is using Protocol Encryption (all traffic)
|
||||||
|
if (isRC4Encrypted()) {
|
||||||
|
m_flags += "E ";
|
||||||
|
m_flagsDescription += tr("encrypted traffic");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//e = Peer is using Protocol Encryption (handshake)
|
||||||
|
if (isPlaintextEncrypted()) {
|
||||||
|
m_flags += "e ";
|
||||||
|
m_flagsDescription += tr("encrypted handshake");
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//P = Peer is using uTorrent uTP
|
||||||
|
|
||||||
|
if (useUTPSocket()) {
|
||||||
|
m_flags += "P ";
|
||||||
|
m_flagsDescription += QString::fromUtf8(C_UTP);
|
||||||
|
m_flagsDescription += ", ";
|
||||||
|
}
|
||||||
|
|
||||||
|
//L = Peer is local
|
||||||
|
if (fromLSD()) {
|
||||||
|
m_flags += "L";
|
||||||
|
m_flagsDescription += tr("peer from LSD");
|
||||||
|
}
|
||||||
|
|
||||||
|
m_flags = m_flags.trimmed();
|
||||||
|
m_flagsDescription = m_flagsDescription.trimmed();
|
||||||
|
if (m_flagsDescription.endsWith(',', Qt::CaseInsensitive))
|
||||||
|
m_flagsDescription.chop(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
QString PeerInfo::flags() const
|
||||||
|
{
|
||||||
|
return m_flags;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString PeerInfo::flagsDescription() const
|
||||||
|
{
|
||||||
|
return m_flagsDescription;
|
||||||
|
}
|
||||||
|
@ -33,9 +33,12 @@
|
|||||||
|
|
||||||
#include <QHostAddress>
|
#include <QHostAddress>
|
||||||
#include <QBitArray>
|
#include <QBitArray>
|
||||||
|
#include <QCoreApplication>
|
||||||
|
|
||||||
namespace BitTorrent
|
namespace BitTorrent
|
||||||
{
|
{
|
||||||
|
class TorrentHandle;
|
||||||
|
|
||||||
struct PeerAddress
|
struct PeerAddress
|
||||||
{
|
{
|
||||||
QHostAddress ip;
|
QHostAddress ip;
|
||||||
@ -47,8 +50,10 @@ namespace BitTorrent
|
|||||||
|
|
||||||
class PeerInfo
|
class PeerInfo
|
||||||
{
|
{
|
||||||
|
Q_DECLARE_TR_FUNCTIONS(PeerInfo)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
PeerInfo(const libtorrent::peer_info &nativeInfo);
|
PeerInfo(const TorrentHandle *torrent, const libtorrent::peer_info &nativeInfo);
|
||||||
|
|
||||||
bool fromDHT() const;
|
bool fromDHT() const;
|
||||||
bool fromPeX() const;
|
bool fromPeX() const;
|
||||||
@ -89,12 +94,21 @@ namespace BitTorrent
|
|||||||
qlonglong totalDownload() const;
|
qlonglong totalDownload() const;
|
||||||
QBitArray pieces() const;
|
QBitArray pieces() const;
|
||||||
QString connectionType() const;
|
QString connectionType() const;
|
||||||
|
qreal relevance() const;
|
||||||
|
QString flags() const;
|
||||||
|
QString flagsDescription() const;
|
||||||
#ifndef DISABLE_COUNTRIES_RESOLUTION
|
#ifndef DISABLE_COUNTRIES_RESOLUTION
|
||||||
QString country() const;
|
QString country() const;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
void calcRelevance(const TorrentHandle *torrent);
|
||||||
|
void determineFlags();
|
||||||
|
|
||||||
libtorrent::peer_info m_nativeInfo;
|
libtorrent::peer_info m_nativeInfo;
|
||||||
|
qreal m_relevance;
|
||||||
|
QString m_flags;
|
||||||
|
QString m_flagsDescription;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -960,7 +960,7 @@ QList<PeerInfo> TorrentHandle::peers() const
|
|||||||
SAFE_CALL(get_peer_info, nativePeers);
|
SAFE_CALL(get_peer_info, nativePeers);
|
||||||
|
|
||||||
foreach (const libt::peer_info &peer, nativePeers)
|
foreach (const libt::peer_info &peer, nativePeers)
|
||||||
peers << peer;
|
peers << PeerInfo(this, peer);
|
||||||
|
|
||||||
return peers;
|
return peers;
|
||||||
}
|
}
|
||||||
|
@ -328,17 +328,15 @@ QStandardItem* PeerListWidget::addPeer(const QString& ip, BitTorrent::TorrentHan
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CONNECTION), peer.connectionType());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CONNECTION), peer.connectionType());
|
||||||
QString flags, tooltip;
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flags());
|
||||||
getFlags(peer, flags, tooltip);
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flagsDescription(), Qt::ToolTipRole);
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), flags);
|
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), tooltip, Qt::ToolTipRole);
|
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CLIENT), peer.client());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CLIENT), peer.client());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PROGRESS), peer.progress());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PROGRESS), peer.progress());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::DOWN_SPEED), peer.payloadDownSpeed());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::DOWN_SPEED), peer.payloadDownSpeed());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::UP_SPEED), peer.payloadUpSpeed());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::UP_SPEED), peer.payloadUpSpeed());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_DOWN), peer.totalDownload());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_DOWN), peer.totalDownload());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_UP), peer.totalUpload());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_UP), peer.totalUpload());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::RELEVANCE), getPeerRelevance(torrent->pieces(), peer.pieces()));
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::RELEVANCE), peer.relevance());
|
||||||
return m_listModel->item(row, PeerListDelegate::IP);
|
return m_listModel->item(row, PeerListDelegate::IP);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -356,18 +354,16 @@ void PeerListWidget::updatePeer(const QString &ip, BitTorrent::TorrentHandle *co
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CONNECTION), peer.connectionType());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CONNECTION), peer.connectionType());
|
||||||
QString flags, tooltip;
|
|
||||||
getFlags(peer, flags, tooltip);
|
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PORT), peer.address().port);
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PORT), peer.address().port);
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), flags);
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flags());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), tooltip, Qt::ToolTipRole);
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flagsDescription(), Qt::ToolTipRole);
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CLIENT), peer.client());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CLIENT), peer.client());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PROGRESS), peer.progress());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PROGRESS), peer.progress());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::DOWN_SPEED), peer.payloadDownSpeed());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::DOWN_SPEED), peer.payloadDownSpeed());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::UP_SPEED), peer.payloadUpSpeed());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::UP_SPEED), peer.payloadUpSpeed());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_DOWN), peer.totalDownload());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_DOWN), peer.totalDownload());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_UP), peer.totalUpload());
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::TOT_UP), peer.totalUpload());
|
||||||
m_listModel->setData(m_listModel->index(row, PeerListDelegate::RELEVANCE), getPeerRelevance(torrent->pieces(), peer.pieces()));
|
m_listModel->setData(m_listModel->index(row, PeerListDelegate::RELEVANCE), peer.relevance());
|
||||||
}
|
}
|
||||||
|
|
||||||
void PeerListWidget::handleResolved(const QString &ip, const QString &hostname)
|
void PeerListWidget::handleResolved(const QString &ip, const QString &hostname)
|
||||||
@ -390,136 +386,3 @@ void PeerListWidget::handleSortColumnChanged(int col)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void PeerListWidget::getFlags(const BitTorrent::PeerInfo &peer, QString& flags, QString& tooltip)
|
|
||||||
{
|
|
||||||
if (peer.isInteresting()) {
|
|
||||||
//d = Your client wants to download, but peer doesn't want to send (interested and choked)
|
|
||||||
if (peer.isRemoteChocked()) {
|
|
||||||
flags += "d ";
|
|
||||||
tooltip += tr("interested(local) and choked(peer)");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
//D = Currently downloading (interested and not choked)
|
|
||||||
flags += "D ";
|
|
||||||
tooltip += tr("interested(local) and unchoked(peer)");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (peer.isRemoteInterested()) {
|
|
||||||
//u = Peer wants your client to upload, but your client doesn't want to (interested and choked)
|
|
||||||
if (peer.isChocked()) {
|
|
||||||
flags += "u ";
|
|
||||||
tooltip += tr("interested(peer) and choked(local)");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
//U = Currently uploading (interested and not choked)
|
|
||||||
flags += "U ";
|
|
||||||
tooltip += tr("interested(peer) and unchoked(local)");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//O = Optimistic unchoke
|
|
||||||
if (peer.optimisticUnchoke()) {
|
|
||||||
flags += "O ";
|
|
||||||
tooltip += tr("optimistic unchoke");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//S = Peer is snubbed
|
|
||||||
if (peer.isSnubbed()) {
|
|
||||||
flags += "S ";
|
|
||||||
tooltip += tr("peer snubbed");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//I = Peer is an incoming connection
|
|
||||||
if (!peer.isLocalConnection()) {
|
|
||||||
flags += "I ";
|
|
||||||
tooltip += tr("incoming connection");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//K = Peer is unchoking your client, but your client is not interested
|
|
||||||
if (!peer.isRemoteChocked() && !peer.isInteresting()) {
|
|
||||||
flags += "K ";
|
|
||||||
tooltip += tr("not interested(local) and unchoked(peer)");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//? = Your client unchoked the peer but the peer is not interested
|
|
||||||
if (!peer.isChocked() && !peer.isRemoteInterested()) {
|
|
||||||
flags += "? ";
|
|
||||||
tooltip += tr("not interested(peer) and unchoked(local)");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//X = Peer was included in peerlists obtained through Peer Exchange (PEX)
|
|
||||||
if (peer.fromPeX()) {
|
|
||||||
flags += "X ";
|
|
||||||
tooltip += tr("peer from PEX");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//H = Peer was obtained through DHT
|
|
||||||
if (peer.fromDHT()) {
|
|
||||||
flags += "H ";
|
|
||||||
tooltip += tr("peer from DHT");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//E = Peer is using Protocol Encryption (all traffic)
|
|
||||||
if (peer.isRC4Encrypted()) {
|
|
||||||
flags += "E ";
|
|
||||||
tooltip += tr("encrypted traffic");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//e = Peer is using Protocol Encryption (handshake)
|
|
||||||
if (peer.isPlaintextEncrypted()) {
|
|
||||||
flags += "e ";
|
|
||||||
tooltip += tr("encrypted handshake");
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//P = Peer is using uTorrent uTP
|
|
||||||
|
|
||||||
if (peer.useUTPSocket()) {
|
|
||||||
flags += "P ";
|
|
||||||
tooltip += QString::fromUtf8(C_UTP);
|
|
||||||
tooltip += ", ";
|
|
||||||
}
|
|
||||||
|
|
||||||
//L = Peer is local
|
|
||||||
if (peer.fromLSD()) {
|
|
||||||
flags += "L";
|
|
||||||
tooltip += tr("peer from LSD");
|
|
||||||
}
|
|
||||||
|
|
||||||
flags = flags.trimmed();
|
|
||||||
tooltip = tooltip.trimmed();
|
|
||||||
if (tooltip.endsWith(',', Qt::CaseInsensitive))
|
|
||||||
tooltip.chop(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
qreal PeerListWidget::getPeerRelevance(const QBitArray &allPieces, const QBitArray &peerPieces)
|
|
||||||
{
|
|
||||||
int localMissing = 0;
|
|
||||||
int remoteHaves = 0;
|
|
||||||
|
|
||||||
for (int i = 0; i < allPieces.size(); ++i) {
|
|
||||||
if (!allPieces[i]) {
|
|
||||||
++localMissing;
|
|
||||||
if (peerPieces[i])
|
|
||||||
++remoteHaves;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (localMissing == 0)
|
|
||||||
return 0.0;
|
|
||||||
|
|
||||||
return static_cast<qreal>(remoteHaves) / localMissing;
|
|
||||||
}
|
|
||||||
|
@ -83,10 +83,6 @@ private slots:
|
|||||||
void copySelectedPeers();
|
void copySelectedPeers();
|
||||||
void handleSortColumnChanged(int col);
|
void handleSortColumnChanged(int col);
|
||||||
|
|
||||||
private:
|
|
||||||
static void getFlags(const BitTorrent::PeerInfo &peer, QString &flags, QString &tooltip);
|
|
||||||
qreal getPeerRelevance(const QBitArray &allPieces, const QBitArray &peerPieces);
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QStandardItemModel *m_listModel;
|
QStandardItemModel *m_listModel;
|
||||||
PeerListDelegate *m_listDelegate;
|
PeerListDelegate *m_listDelegate;
|
||||||
|
@ -36,7 +36,9 @@
|
|||||||
#include "base/bittorrent/sessionstatus.h"
|
#include "base/bittorrent/sessionstatus.h"
|
||||||
#include "base/bittorrent/torrenthandle.h"
|
#include "base/bittorrent/torrenthandle.h"
|
||||||
#include "base/bittorrent/trackerentry.h"
|
#include "base/bittorrent/trackerentry.h"
|
||||||
|
#include "base/bittorrent/peerinfo.h"
|
||||||
#include "base/torrentfilter.h"
|
#include "base/torrentfilter.h"
|
||||||
|
#include "base/net/geoipmanager.h"
|
||||||
#include "jsonutils.h"
|
#include "jsonutils.h"
|
||||||
|
|
||||||
#include <QDebug>
|
#include <QDebug>
|
||||||
@ -105,6 +107,22 @@ static const char KEY_TORRENT_SUPER_SEEDING[] = "super_seeding";
|
|||||||
static const char KEY_TORRENT_FORCE_START[] = "force_start";
|
static const char KEY_TORRENT_FORCE_START[] = "force_start";
|
||||||
static const char KEY_TORRENT_SAVE_PATH[] = "save_path";
|
static const char KEY_TORRENT_SAVE_PATH[] = "save_path";
|
||||||
|
|
||||||
|
// Peer keys
|
||||||
|
static const char KEY_PEER_IP[] = "ip";
|
||||||
|
static const char KEY_PEER_PORT[] = "port";
|
||||||
|
static const char KEY_PEER_COUNTRY_CODE[] = "country_code";
|
||||||
|
static const char KEY_PEER_COUNTRY[] = "country";
|
||||||
|
static const char KEY_PEER_CLIENT[] = "client";
|
||||||
|
static const char KEY_PEER_PROGRESS[] = "progress";
|
||||||
|
static const char KEY_PEER_DOWN_SPEED[] = "dl_speed";
|
||||||
|
static const char KEY_PEER_UP_SPEED[] = "up_speed";
|
||||||
|
static const char KEY_PEER_TOT_DOWN[] = "downloaded";
|
||||||
|
static const char KEY_PEER_TOT_UP[] = "uploaded";
|
||||||
|
static const char KEY_PEER_CONNECTION_TYPE[] = "connection";
|
||||||
|
static const char KEY_PEER_FLAGS[] = "flags";
|
||||||
|
static const char KEY_PEER_FLAGS_DESCRIPTION[] = "flags_desc";
|
||||||
|
static const char KEY_PEER_RELEVANCE[] = "relevance";
|
||||||
|
|
||||||
// Tracker keys
|
// Tracker keys
|
||||||
static const char KEY_TRACKER_URL[] = "url";
|
static const char KEY_TRACKER_URL[] = "url";
|
||||||
static const char KEY_TRACKER_STATUS[] = "status";
|
static const char KEY_TRACKER_STATUS[] = "status";
|
||||||
@ -171,6 +189,9 @@ static const char KEY_SYNC_MAINDATA_QUEUEING[] = "queueing";
|
|||||||
static const char KEY_SYNC_MAINDATA_USE_ALT_SPEED_LIMITS[] = "use_alt_speed_limits";
|
static const char KEY_SYNC_MAINDATA_USE_ALT_SPEED_LIMITS[] = "use_alt_speed_limits";
|
||||||
static const char KEY_SYNC_MAINDATA_REFRESH_INTERVAL[] = "refresh_interval";
|
static const char KEY_SYNC_MAINDATA_REFRESH_INTERVAL[] = "refresh_interval";
|
||||||
|
|
||||||
|
// Sync torrent peers keys
|
||||||
|
static const char KEY_SYNC_TORRENT_PEERS_SHOW_FLAGS[] = "show_flags";
|
||||||
|
|
||||||
static const char KEY_FULL_UPDATE[] = "full_update";
|
static const char KEY_FULL_UPDATE[] = "full_update";
|
||||||
static const char KEY_RESPONSE_ID[] = "rid";
|
static const char KEY_RESPONSE_ID[] = "rid";
|
||||||
static const char KEY_SUFFIX_REMOVED[] = "_removed";
|
static const char KEY_SUFFIX_REMOVED[] = "_removed";
|
||||||
@ -354,6 +375,54 @@ QByteArray btjson::getSyncMainData(int acceptedResponseId, QVariantMap &lastData
|
|||||||
return json::toJson(generateSyncData(acceptedResponseId, data, lastAcceptedData, lastData));
|
return json::toJson(generateSyncData(acceptedResponseId, data, lastAcceptedData, lastData));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QByteArray btjson::getSyncTorrentPeersData(int acceptedResponseId, QString hash, QVariantMap &lastData, QVariantMap &lastAcceptedData)
|
||||||
|
{
|
||||||
|
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
|
||||||
|
if (!torrent) {
|
||||||
|
qWarning() << Q_FUNC_INFO << "Invalid torrent " << qPrintable(hash);
|
||||||
|
return QByteArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
QVariantMap data;
|
||||||
|
QVariantHash peers;
|
||||||
|
QList<BitTorrent::PeerInfo> peersList = torrent->peers();
|
||||||
|
#ifndef DISABLE_COUNTRIES_RESOLUTION
|
||||||
|
bool resolvePeerCountries = Preferences::instance()->resolvePeerCountries();
|
||||||
|
#else
|
||||||
|
bool resolvePeerCountries = false;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
data[KEY_SYNC_TORRENT_PEERS_SHOW_FLAGS] = resolvePeerCountries;
|
||||||
|
|
||||||
|
foreach (const BitTorrent::PeerInfo &pi, peersList) {
|
||||||
|
if (pi.address().ip.isNull()) continue;
|
||||||
|
QVariantMap peer;
|
||||||
|
#ifndef DISABLE_COUNTRIES_RESOLUTION
|
||||||
|
if (resolvePeerCountries) {
|
||||||
|
peer[KEY_PEER_COUNTRY_CODE] = pi.country().toLower();
|
||||||
|
peer[KEY_PEER_COUNTRY] = Net::GeoIPManager::CountryName(pi.country());
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
peer[KEY_PEER_IP] = pi.address().ip.toString();
|
||||||
|
peer[KEY_PEER_PORT] = pi.address().port;
|
||||||
|
peer[KEY_PEER_CLIENT] = pi.client();
|
||||||
|
peer[KEY_PEER_PROGRESS] = pi.progress();
|
||||||
|
peer[KEY_PEER_DOWN_SPEED] = pi.payloadDownSpeed();
|
||||||
|
peer[KEY_PEER_UP_SPEED] = pi.payloadUpSpeed();
|
||||||
|
peer[KEY_PEER_TOT_DOWN] = pi.totalDownload();
|
||||||
|
peer[KEY_PEER_TOT_UP] = pi.totalUpload();
|
||||||
|
peer[KEY_PEER_CONNECTION_TYPE] = pi.connectionType();
|
||||||
|
peer[KEY_PEER_FLAGS] = pi.flags();
|
||||||
|
peer[KEY_PEER_FLAGS_DESCRIPTION] = pi.flagsDescription();
|
||||||
|
peer[KEY_PEER_RELEVANCE] = pi.relevance();
|
||||||
|
peers[pi.address().ip.toString() + ":" + QString::number(pi.address().port)] = peer;
|
||||||
|
}
|
||||||
|
|
||||||
|
data["peers"] = peers;
|
||||||
|
|
||||||
|
return json::toJson(generateSyncData(acceptedResponseId, data, lastAcceptedData, lastData));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the trackers for a torrent in JSON format.
|
* Returns the trackers for a torrent in JSON format.
|
||||||
*
|
*
|
||||||
@ -610,7 +679,7 @@ QByteArray btjson::getTorrentsRatesLimits(QStringList &hashes, bool downloadLimi
|
|||||||
map[hash] = limit;
|
map[hash] = limit;
|
||||||
}
|
}
|
||||||
|
|
||||||
return json::toJson(map);
|
return json::toJson(map);
|
||||||
}
|
}
|
||||||
|
|
||||||
QVariantMap toMap(BitTorrent::TorrentHandle *const torrent)
|
QVariantMap toMap(BitTorrent::TorrentHandle *const torrent)
|
||||||
|
@ -46,6 +46,7 @@ public:
|
|||||||
static QByteArray getTorrents(QString filter = "all", QString label = QString(),
|
static QByteArray getTorrents(QString filter = "all", QString label = QString(),
|
||||||
QString sortedColumn = "name", bool reverse = false, int limit = 0, int offset = 0);
|
QString sortedColumn = "name", bool reverse = false, int limit = 0, int offset = 0);
|
||||||
static QByteArray getSyncMainData(int acceptedResponseId, QVariantMap &lastData, QVariantMap &lastAcceptedData);
|
static QByteArray getSyncMainData(int acceptedResponseId, QVariantMap &lastData, QVariantMap &lastAcceptedData);
|
||||||
|
static QByteArray getSyncTorrentPeersData(int acceptedResponseId, QString hash, QVariantMap &lastData, QVariantMap &lastAcceptedData);
|
||||||
static QByteArray getTrackersForTorrent(const QString& hash);
|
static QByteArray getTrackersForTorrent(const QString& hash);
|
||||||
static QByteArray getWebSeedsForTorrent(const QString& hash);
|
static QByteArray getWebSeedsForTorrent(const QString& hash);
|
||||||
static QByteArray getPropertiesForTorrent(const QString& hash);
|
static QByteArray getPropertiesForTorrent(const QString& hash);
|
||||||
|
@ -82,6 +82,7 @@ QMap<QString, QMap<QString, WebApplication::Action> > WebApplication::initialize
|
|||||||
ADD_ACTION(query, propertiesWebSeeds);
|
ADD_ACTION(query, propertiesWebSeeds);
|
||||||
ADD_ACTION(query, propertiesFiles);
|
ADD_ACTION(query, propertiesFiles);
|
||||||
ADD_ACTION(sync, maindata);
|
ADD_ACTION(sync, maindata);
|
||||||
|
ADD_ACTION(sync, torrent_peers);
|
||||||
ADD_ACTION(command, shutdown);
|
ADD_ACTION(command, shutdown);
|
||||||
ADD_ACTION(command, download);
|
ADD_ACTION(command, download);
|
||||||
ADD_ACTION(command, upload);
|
ADD_ACTION(command, upload);
|
||||||
@ -277,6 +278,19 @@ void WebApplication::action_sync_maindata()
|
|||||||
session()->syncMainDataLastAcceptedResponse), Http::CONTENT_TYPE_JSON);
|
session()->syncMainDataLastAcceptedResponse), Http::CONTENT_TYPE_JSON);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GET param:
|
||||||
|
// - hash (string): torrent hash
|
||||||
|
// - rid (int): last response id
|
||||||
|
void WebApplication::action_sync_torrent_peers()
|
||||||
|
{
|
||||||
|
CHECK_URI(0);
|
||||||
|
print(btjson::getSyncTorrentPeersData(request().gets["rid"].toInt(),
|
||||||
|
request().gets["hash"],
|
||||||
|
session()->syncTorrentPeersLastResponse,
|
||||||
|
session()->syncTorrentPeersLastAcceptedResponse), Http::CONTENT_TYPE_JSON);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void WebApplication::action_version_api()
|
void WebApplication::action_version_api()
|
||||||
{
|
{
|
||||||
CHECK_URI(0);
|
CHECK_URI(0);
|
||||||
|
@ -55,6 +55,7 @@ private:
|
|||||||
void action_query_propertiesWebSeeds();
|
void action_query_propertiesWebSeeds();
|
||||||
void action_query_propertiesFiles();
|
void action_query_propertiesFiles();
|
||||||
void action_sync_maindata();
|
void action_sync_maindata();
|
||||||
|
void action_sync_torrent_peers();
|
||||||
void action_command_shutdown();
|
void action_command_shutdown();
|
||||||
void action_command_download();
|
void action_command_download();
|
||||||
void action_command_upload();
|
void action_command_upload();
|
||||||
|
@ -35,6 +35,8 @@ struct WebSessionData
|
|||||||
{
|
{
|
||||||
QVariantMap syncMainDataLastResponse;
|
QVariantMap syncMainDataLastResponse;
|
||||||
QVariantMap syncMainDataLastAcceptedResponse;
|
QVariantMap syncMainDataLastAcceptedResponse;
|
||||||
|
QVariantMap syncTorrentPeersLastResponse;
|
||||||
|
QVariantMap syncTorrentPeersLastAcceptedResponse;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // WEBSESSIONDATA
|
#endif // WEBSESSIONDATA
|
||||||
|
Loading…
x
Reference in New Issue
Block a user