Skip to content

Commit

Permalink
test: [#1240] add tests for InMemoryTorrentRepository. WIP
Browse files Browse the repository at this point in the history
  • Loading branch information
josecelano committed Feb 5, 2025
1 parent 806dcc4 commit cdaa1e0
Showing 1 changed file with 130 additions and 27 deletions.
157 changes: 130 additions & 27 deletions packages/tracker-core/src/torrent/repository/in_memory.rs
Original file line number Diff line number Diff line change
Expand Up @@ -127,25 +127,51 @@ mod tests {

// The `InMemoryTorrentRepository` has these responsibilities:
// - To maintain the peer lists for each torrent.
// - To return the peer lists for a given torrent.
// - To return the torrent entries, which contains all the info about the
// - To maintain the the torrent entries, which contains all the info about the
// torrents, including the peer lists.
// - To return the torrent entries.
// - To return the peer lists for a given torrent.
// - To return the torrent metrics.
// - To return the swarm metadata for a given torrent.
// - To handle the persistence of the torrent entries.

mod maintaining_the_peer_lists {
// Methods:
// - upsert_peer
// - remove
// - remove_inactive_peers
// - remove_peerless_torrents
// - [x] upsert_peer

use std::sync::Arc;

use crate::core_tests::{sample_info_hash, sample_peer};
use crate::torrent::repository::in_memory::InMemoryTorrentRepository;

#[tokio::test]
async fn it_should_add_the_first_peer_to_the_torrent_peer_list() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());

let info_hash = sample_info_hash();

let () = in_memory_torrent_repository.upsert_peer(&info_hash, &sample_peer());

assert!(in_memory_torrent_repository.get(&info_hash).is_some());
}

#[tokio::test]
async fn it_should_allow_adding_the_same_peer_twice_to_the_torrent_peer_list() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());

let info_hash = sample_info_hash();

let () = in_memory_torrent_repository.upsert_peer(&info_hash, &sample_peer());
let () = in_memory_torrent_repository.upsert_peer(&info_hash, &sample_peer());

assert!(in_memory_torrent_repository.get(&info_hash).is_some());
}
}

mod returning_peer_lists_for_a_torrent {
// Methods:
// - get_peers_for
// - get_torrent_peers
// - [x] get_torrent_peers
// - [x] get_peers_for

use std::net::{IpAddr, Ipv4Addr, SocketAddr};
use std::sync::Arc;
Expand All @@ -159,6 +185,20 @@ mod tests {
use crate::torrent::repository::in_memory::tests::numeric_peer_id;
use crate::torrent::repository::in_memory::InMemoryTorrentRepository;

#[tokio::test]
async fn it_should_return_the_peers_for_a_given_torrent() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());

let info_hash = sample_info_hash();
let peer = sample_peer();

let () = in_memory_torrent_repository.upsert_peer(&info_hash, &peer);

let peers = in_memory_torrent_repository.get_torrent_peers(&info_hash);

assert_eq!(peers, vec![Arc::new(peer)]);
}

#[tokio::test]
async fn it_should_return_74_peers_at_the_most_for_a_given_torrent() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());
Expand All @@ -184,20 +224,6 @@ mod tests {
assert_eq!(peers.len(), 74);
}

#[tokio::test]
async fn it_should_return_the_peers_for_a_given_torrent() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());

let info_hash = sample_info_hash();
let peer = sample_peer();

let () = in_memory_torrent_repository.upsert_peer(&info_hash, &peer);

let peers = in_memory_torrent_repository.get_torrent_peers(&info_hash);

assert_eq!(peers, vec![Arc::new(peer)]);
}

#[tokio::test]
async fn it_should_return_the_peers_for_a_given_torrent_excluding_a_given_peer() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());
Expand Down Expand Up @@ -243,15 +269,92 @@ mod tests {
}
}

mod maintaining_the_torrent_entries {
// Methods:
// - [x] remove
// - [x] remove_inactive_peers
// - [x] remove_peerless_torrents

use std::ops::Add;
use std::sync::Arc;
use std::time::Duration;

use bittorrent_primitives::info_hash::InfoHash;
use torrust_tracker_configuration::TrackerPolicy;
use torrust_tracker_primitives::DurationSinceUnixEpoch;

use crate::core_tests::{sample_info_hash, sample_peer};
use crate::torrent::repository::in_memory::InMemoryTorrentRepository;

#[tokio::test]
async fn it_should_remove_a_torrent_entry() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());

let info_hash = sample_info_hash();
let () = in_memory_torrent_repository.upsert_peer(&info_hash, &sample_peer());

let _unused = in_memory_torrent_repository.remove(&info_hash);

assert!(in_memory_torrent_repository.get(&info_hash).is_none());
}

#[tokio::test]
async fn it_should_remove_peers_that_have_not_been_updated_after_a_cutoff_time() {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());

let info_hash = sample_info_hash();
let mut peer = sample_peer();
peer.updated = DurationSinceUnixEpoch::new(0, 0);

let () = in_memory_torrent_repository.upsert_peer(&info_hash, &peer);

// Cut off time is 1 second after the peer was updated
in_memory_torrent_repository.remove_inactive_peers(peer.updated.add(Duration::from_secs(1)));

assert!(!in_memory_torrent_repository
.get_torrent_peers(&info_hash)
.contains(&Arc::new(peer)));
}

fn initialize_repository_with_one_torrent_without_peers(info_hash: &InfoHash) -> Arc<InMemoryTorrentRepository> {
let in_memory_torrent_repository = Arc::new(InMemoryTorrentRepository::default());

// Insert a sample peer for the torrent to force adding the torrent entry
let mut peer = sample_peer();
peer.updated = DurationSinceUnixEpoch::new(0, 0);
let () = in_memory_torrent_repository.upsert_peer(info_hash, &peer);

// Remove the peer
in_memory_torrent_repository.remove_inactive_peers(peer.updated.add(Duration::from_secs(1)));

in_memory_torrent_repository
}

#[tokio::test]
async fn it_should_remove_torrents_without_peers() {
let info_hash = sample_info_hash();

let in_memory_torrent_repository = initialize_repository_with_one_torrent_without_peers(&info_hash);

let tracker_policy = TrackerPolicy {
remove_peerless_torrents: true,
..Default::default()
};

in_memory_torrent_repository.remove_peerless_torrents(&tracker_policy);

assert!(in_memory_torrent_repository.get(&info_hash).is_none());
}
}
mod returning_torrent_entries {
// Methods:
// - get
// - get_paginated
// - [ ] get
// - [ ] get_paginated
}

mod returning_torrent_metrics {
// Methods:
// - get_torrents_metrics
// - [ ] get_torrents_metrics

use std::sync::Arc;

Expand Down Expand Up @@ -326,11 +429,11 @@ mod tests {

mod returning_swarm_metadata {
// Methods:
// - get_swarm_metadata
// - [ ] get_swarm_metadata
}

mod handling_persistence {
// Methods:
// - import_persistent
// - [ ] import_persistent
}
}

0 comments on commit cdaa1e0

Please sign in to comment.