@@ -453,8 +453,8 @@ use torrust_tracker_primitives::TrackerMode;
453
453
use self :: auth:: Key ;
454
454
use self :: error:: Error ;
455
455
use self :: peer:: Peer ;
456
- use self :: torrent:: repository:: { RepositoryAsyncSingle , TRepositoryAsync } ;
457
456
use crate :: core:: databases:: Database ;
457
+ use crate :: core:: torrent:: repository:: { Repository , RepositoryDashmap } ;
458
458
use crate :: core:: torrent:: { SwarmMetadata , SwarmStats } ;
459
459
use crate :: shared:: bit_torrent:: info_hash:: InfoHash ;
460
460
@@ -479,7 +479,7 @@ pub struct Tracker {
479
479
mode : TrackerMode ,
480
480
keys : tokio:: sync:: RwLock < std:: collections:: HashMap < Key , auth:: ExpiringKey > > ,
481
481
whitelist : tokio:: sync:: RwLock < std:: collections:: HashSet < InfoHash > > ,
482
- pub torrents : Arc < RepositoryAsyncSingle > ,
482
+ pub torrent_repository : Arc < RepositoryDashmap > ,
483
483
stats_event_sender : Option < Box < dyn statistics:: EventSender > > ,
484
484
stats_repository : statistics:: Repo ,
485
485
}
@@ -574,7 +574,7 @@ impl Tracker {
574
574
mode,
575
575
keys : tokio:: sync:: RwLock :: new ( std:: collections:: HashMap :: new ( ) ) ,
576
576
whitelist : tokio:: sync:: RwLock :: new ( std:: collections:: HashSet :: new ( ) ) ,
577
- torrents : Arc :: new ( RepositoryAsyncSingle :: new ( ) ) ,
577
+ torrent_repository : Arc :: new ( RepositoryDashmap :: new ( ) ) ,
578
578
stats_event_sender,
579
579
stats_repository,
580
580
database,
@@ -657,9 +657,7 @@ impl Tracker {
657
657
658
658
/// It returns the data for a `scrape` response.
659
659
async fn get_swarm_metadata ( & self , info_hash : & InfoHash ) -> SwarmMetadata {
660
- let torrents = self . torrents . get_torrents ( ) . await ;
661
-
662
- match torrents. get ( info_hash) {
660
+ match & self . torrent_repository . torrents . get ( info_hash) {
663
661
Some ( torrent_entry) => torrent_entry. get_swarm_metadata ( ) ,
664
662
None => SwarmMetadata :: default ( ) ,
665
663
}
@@ -676,11 +674,9 @@ impl Tracker {
676
674
pub async fn load_torrents_from_database ( & self ) -> Result < ( ) , databases:: error:: Error > {
677
675
let persistent_torrents = self . database . load_persistent_torrents ( ) . await ?;
678
676
679
- let mut torrents = self . torrents . get_torrents_mut ( ) . await ;
680
-
681
677
for ( info_hash, completed) in persistent_torrents {
682
678
// Skip if torrent entry already exists
683
- if torrents. contains_key ( & info_hash) {
679
+ if self . torrent_repository . torrents . contains_key ( & info_hash) {
684
680
continue ;
685
681
}
686
682
@@ -689,16 +685,14 @@ impl Tracker {
689
685
completed,
690
686
} ;
691
687
692
- torrents. insert ( info_hash, torrent_entry) ;
688
+ self . torrent_repository . torrents . insert ( info_hash, torrent_entry) ;
693
689
}
694
690
695
691
Ok ( ( ) )
696
692
}
697
693
698
694
async fn get_torrent_peers_for_peer ( & self , info_hash : & InfoHash , peer : & Peer ) -> Vec < peer:: Peer > {
699
- let read_lock = self . torrents . get_torrents ( ) . await ;
700
-
701
- match read_lock. get ( info_hash) {
695
+ match & self . torrent_repository . torrents . get ( info_hash) {
702
696
None => vec ! [ ] ,
703
697
Some ( entry) => entry
704
698
. get_peers_for_peer ( peer, TORRENT_PEERS_LIMIT )
@@ -712,9 +706,7 @@ impl Tracker {
712
706
///
713
707
/// Get all torrent peers for a given torrent
714
708
pub async fn get_torrent_peers ( & self , info_hash : & InfoHash ) -> Vec < peer:: Peer > {
715
- let read_lock = self . torrents . get_torrents ( ) . await ;
716
-
717
- match read_lock. get ( info_hash) {
709
+ match & self . torrent_repository . torrents . get ( info_hash) {
718
710
None => vec ! [ ] ,
719
711
Some ( entry) => entry. get_peers ( TORRENT_PEERS_LIMIT ) . into_iter ( ) . copied ( ) . collect ( ) ,
720
712
}
@@ -729,7 +721,9 @@ impl Tracker {
729
721
// code-review: consider splitting the function in two (command and query segregation).
730
722
// `update_torrent_with_peer` and `get_stats`
731
723
732
- let ( stats, stats_updated) = self . torrents . update_torrent_with_peer_and_get_stats ( info_hash, peer) . await ;
724
+ let ( stats, stats_updated) = self
725
+ . torrent_repository
726
+ . update_torrent_with_peer_and_get_stats ( info_hash, peer) ;
733
727
734
728
if self . config . persistent_torrent_completed_stat && stats_updated {
735
729
let completed = stats. completed ;
@@ -756,12 +750,12 @@ impl Tracker {
756
750
torrents : 0 ,
757
751
} ) ) ;
758
752
759
- let db = self . torrents . get_torrents ( ) . await . clone ( ) ;
753
+ let torrents = & self . torrent_repository . torrents ;
760
754
761
- let futures = db
762
- . values ( )
763
- . map ( |torrent_entry | {
764
- let torrent_entry = torrent_entry . clone ( ) ;
755
+ let futures = torrents
756
+ . iter ( )
757
+ . map ( |rm | {
758
+ let torrent_entry = rm . value ( ) . clone ( ) ;
765
759
let torrents_metrics = arc_torrents_metrics. clone ( ) ;
766
760
767
761
async move {
@@ -789,34 +783,21 @@ impl Tracker {
789
783
///
790
784
/// # Context: Tracker
791
785
pub async fn cleanup_torrents ( & self ) {
792
- let mut torrents_lock = self . torrents . get_torrents_mut ( ) . await ;
786
+ self . remove_all_inactive_peers_for_torrents ( ) ;
793
787
794
- // If we don't need to remove torrents we will use the faster iter
795
788
if self . config . remove_peerless_torrents {
796
- let mut cleaned_torrents_map: BTreeMap < InfoHash , torrent:: Entry > = BTreeMap :: new ( ) ;
797
-
798
- for ( info_hash, torrent_entry) in & mut * torrents_lock {
799
- torrent_entry. remove_inactive_peers ( self . config . max_peer_timeout ) ;
800
-
801
- if torrent_entry. peers . is_empty ( ) {
802
- continue ;
803
- }
804
-
805
- if self . config . persistent_torrent_completed_stat && torrent_entry. completed == 0 {
806
- continue ;
807
- }
808
-
809
- cleaned_torrents_map. insert ( * info_hash, torrent_entry. clone ( ) ) ;
810
- }
811
-
812
- * torrents_lock = cleaned_torrents_map;
813
- } else {
814
- for torrent_entry in ( * torrents_lock) . values_mut ( ) {
815
- torrent_entry. remove_inactive_peers ( self . config . max_peer_timeout ) ;
816
- }
789
+ self . torrent_repository
790
+ . torrents
791
+ . retain ( |_, torrent_entry| !torrent_entry. peers . is_empty ( ) ) ;
817
792
}
818
793
}
819
794
795
+ pub fn remove_all_inactive_peers_for_torrents ( & self ) {
796
+ self . torrent_repository . torrents . iter_mut ( ) . for_each ( |mut rm| {
797
+ rm. value_mut ( ) . remove_inactive_peers ( self . config . max_peer_timeout ) ;
798
+ } )
799
+ }
800
+
820
801
/// It authenticates the peer `key` against the `Tracker` authentication
821
802
/// key list.
822
803
///
@@ -1746,11 +1727,11 @@ mod tests {
1746
1727
assert_eq ! ( swarm_stats. completed, 1 ) ;
1747
1728
1748
1729
// Remove the newly updated torrent from memory
1749
- tracker. torrents . get_torrents_mut ( ) . await . remove ( & info_hash) ;
1730
+ tracker. torrent_repository . torrents . remove ( & info_hash) ;
1750
1731
1751
1732
tracker. load_torrents_from_database ( ) . await . unwrap ( ) ;
1752
1733
1753
- let torrents = tracker. torrents . get_torrents ( ) . await ;
1734
+ let torrents = & tracker. torrent_repository . torrents ;
1754
1735
assert ! ( torrents. contains_key( & info_hash) ) ;
1755
1736
1756
1737
let torrent_entry = torrents. get ( & info_hash) . unwrap ( ) ;
0 commit comments