From 44255e243c062ad2a101a426c9c02f03b1cfb5d2 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 16:45:36 +0000 Subject: [PATCH 01/18] refactor: [#1195] create dir for mod We will add more submodules. --- src/core/authentication/{key.rs => key/mod.rs} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename src/core/authentication/{key.rs => key/mod.rs} (100%) diff --git a/src/core/authentication/key.rs b/src/core/authentication/key/mod.rs similarity index 100% rename from src/core/authentication/key.rs rename to src/core/authentication/key/mod.rs From f4c7b9746562a45331d108b11ebe7dc794253a2a Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 17:08:47 +0000 Subject: [PATCH 02/18] refactor: [#1195] extract DatabaseKeyRepository --- src/core/authentication/key/mod.rs | 1 + src/core/authentication/key/repository/mod.rs | 1 + .../key/repository/persisted.rs | 48 +++++++++++++++++++ src/core/authentication/mod.rs | 23 +++++---- 4 files changed, 64 insertions(+), 9 deletions(-) create mode 100644 src/core/authentication/key/repository/mod.rs create mode 100644 src/core/authentication/key/repository/persisted.rs diff --git a/src/core/authentication/key/mod.rs b/src/core/authentication/key/mod.rs index 8858361ec..49d559e42 100644 --- a/src/core/authentication/key/mod.rs +++ b/src/core/authentication/key/mod.rs @@ -37,6 +37,7 @@ //! //! assert!(authentication::key::verify_key_expiration(&expiring_key).is_ok()); //! ``` +pub mod repository; use std::panic::Location; use std::str::FromStr; diff --git a/src/core/authentication/key/repository/mod.rs b/src/core/authentication/key/repository/mod.rs new file mode 100644 index 000000000..fe3bdd68c --- /dev/null +++ b/src/core/authentication/key/repository/mod.rs @@ -0,0 +1 @@ +pub mod persisted; diff --git a/src/core/authentication/key/repository/persisted.rs b/src/core/authentication/key/repository/persisted.rs new file mode 100644 index 000000000..736a409eb --- /dev/null +++ b/src/core/authentication/key/repository/persisted.rs @@ -0,0 +1,48 @@ +use std::sync::Arc; + +use crate::core::authentication::key::{Key, PeerKey}; +use crate::core::databases::{self, Database}; + +/// The database repository for the authentication keys. +pub struct DatabaseKeyRepository { + database: Arc>, +} + +impl DatabaseKeyRepository { + #[must_use] + pub fn new(database: &Arc>) -> Self { + Self { + database: database.clone(), + } + } + + /// It adds a new key to the database. + /// + /// # Errors + /// + /// Will return a `databases::error::Error` if unable to add the `auth_key` to the database. + pub fn add(&self, peer_key: &PeerKey) -> Result<(), databases::error::Error> { + self.database.add_key_to_keys(peer_key)?; + Ok(()) + } + + /// It removes an key from the database. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to remove the `key` from the database. + pub fn remove(&self, key: &Key) -> Result<(), databases::error::Error> { + self.database.remove_key_from_keys(key)?; + Ok(()) + } + + /// It loads all keys from the database. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to load the keys from the database. + pub fn load_keys(&self) -> Result, databases::error::Error> { + let keys = self.database.load_keys()?; + Ok(keys) + } +} diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index d611ae57e..618f57f91 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -2,6 +2,7 @@ use std::panic::Location; use std::sync::Arc; use std::time::Duration; +use key::repository::persisted::DatabaseKeyRepository; use torrust_tracker_clock::clock::Time; use torrust_tracker_configuration::Core; use torrust_tracker_located_error::Located; @@ -35,12 +36,11 @@ pub struct Facade { /// The tracker configuration. config: Core, - /// A database driver implementation: [`Sqlite3`](crate::core::databases::sqlite) - /// or [`MySQL`](crate::core::databases::mysql) - database: Arc>, - /// Tracker users' keys. Only for private trackers. keys: tokio::sync::RwLock>, + + /// The database repository for the authentication keys. + db_key_repository: DatabaseKeyRepository, } impl Facade { @@ -48,8 +48,8 @@ impl Facade { pub fn new(config: &Core, database: &Arc>) -> Self { Self { config: config.clone(), - database: database.clone(), keys: tokio::sync::RwLock::new(std::collections::HashMap::new()), + db_key_repository: DatabaseKeyRepository::new(database), } } @@ -205,7 +205,8 @@ impl Facade { pub async fn generate_auth_key(&self, lifetime: Option) -> Result { let auth_key = key::generate_key(lifetime); - self.database.add_key_to_keys(&auth_key)?; + self.db_key_repository.add(&auth_key)?; + self.keys.write().await.insert(auth_key.key.clone(), auth_key.clone()); Ok(auth_key) } @@ -254,7 +255,8 @@ impl Facade { // code-review: should we return a friendly error instead of the DB // constrain error when the key already exist? For now, it's returning // the specif error for each DB driver when a UNIQUE constrain fails. - self.database.add_key_to_keys(&auth_key)?; + self.db_key_repository.add(&auth_key)?; + self.keys.write().await.insert(auth_key.key.clone(), auth_key.clone()); Ok(auth_key) } @@ -267,8 +269,10 @@ impl Facade { /// /// Will return a `database::Error` if unable to remove the `key` to the database. pub async fn remove_auth_key(&self, key: &Key) -> Result<(), databases::error::Error> { - self.database.remove_key_from_keys(key)?; + self.db_key_repository.remove(key)?; + self.remove_in_memory_auth_key(key).await; + Ok(()) } @@ -290,7 +294,8 @@ impl Facade { /// /// Will return a `database::Error` if unable to `load_keys` from the database. pub async fn load_keys_from_database(&self) -> Result<(), databases::error::Error> { - let keys_from_database = self.database.load_keys()?; + let keys_from_database = self.db_key_repository.load_keys()?; + let mut keys = self.keys.write().await; keys.clear(); From 12a62ceaef3bdec903f575be00c81c781549f323 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 17:28:12 +0000 Subject: [PATCH 03/18] refactor: [#1195] extract InMemoryKeyRepository --- .../key/repository/in_memory.rs | 30 ++++++++++++++ src/core/authentication/key/repository/mod.rs | 1 + src/core/authentication/mod.rs | 41 ++++++++++--------- 3 files changed, 52 insertions(+), 20 deletions(-) create mode 100644 src/core/authentication/key/repository/in_memory.rs diff --git a/src/core/authentication/key/repository/in_memory.rs b/src/core/authentication/key/repository/in_memory.rs new file mode 100644 index 000000000..266d5a5fb --- /dev/null +++ b/src/core/authentication/key/repository/in_memory.rs @@ -0,0 +1,30 @@ +use crate::core::authentication::key::{Key, PeerKey}; + +/// In-memory implementation of the authentication key repository. +#[derive(Debug, Default)] +pub struct InMemoryKeyRepository { + /// Tracker users' keys. Only for private trackers. + keys: tokio::sync::RwLock>, +} + +impl InMemoryKeyRepository { + /// It adds a new authentication key. + pub async fn insert(&self, auth_key: &PeerKey) { + self.keys.write().await.insert(auth_key.key.clone(), auth_key.clone()); + } + + /// It removes an authentication key. + pub async fn remove(&self, key: &Key) { + self.keys.write().await.remove(key); + } + + pub async fn get(&self, key: &Key) -> Option { + self.keys.read().await.get(key).cloned() + } + + /// It clears all the authentication keys. + pub async fn clear(&self) { + let mut keys = self.keys.write().await; + keys.clear(); + } +} diff --git a/src/core/authentication/key/repository/mod.rs b/src/core/authentication/key/repository/mod.rs index fe3bdd68c..51723b68d 100644 --- a/src/core/authentication/key/repository/mod.rs +++ b/src/core/authentication/key/repository/mod.rs @@ -1 +1,2 @@ +pub mod in_memory; pub mod persisted; diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 618f57f91..4a65a26a7 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -2,6 +2,7 @@ use std::panic::Location; use std::sync::Arc; use std::time::Duration; +use key::repository::in_memory::InMemoryKeyRepository; use key::repository::persisted::DatabaseKeyRepository; use torrust_tracker_clock::clock::Time; use torrust_tracker_configuration::Core; @@ -36,11 +37,11 @@ pub struct Facade { /// The tracker configuration. config: Core, - /// Tracker users' keys. Only for private trackers. - keys: tokio::sync::RwLock>, - /// The database repository for the authentication keys. db_key_repository: DatabaseKeyRepository, + + /// In-memory implementation of the authentication key repository. + in_memory_key_repository: InMemoryKeyRepository, } impl Facade { @@ -48,8 +49,8 @@ impl Facade { pub fn new(config: &Core, database: &Arc>) -> Self { Self { config: config.clone(), - keys: tokio::sync::RwLock::new(std::collections::HashMap::new()), db_key_repository: DatabaseKeyRepository::new(database), + in_memory_key_repository: InMemoryKeyRepository::default(), } } @@ -82,7 +83,7 @@ impl Facade { /// /// Will return a `key::Error` if unable to get any `auth_key`. pub async fn verify_auth_key(&self, key: &Key) -> Result<(), Error> { - match self.keys.read().await.get(key) { + match self.in_memory_key_repository.get(key).await { None => Err(Error::UnableToReadKey { location: Location::caller(), key: Box::new(key.clone()), @@ -90,12 +91,12 @@ impl Facade { Some(key) => match self.config.private_mode { Some(private_mode) => { if private_mode.check_keys_expiration { - return key::verify_key_expiration(key); + return key::verify_key_expiration(&key); } Ok(()) } - None => key::verify_key_expiration(key), + None => key::verify_key_expiration(&key), }, } } @@ -203,12 +204,13 @@ impl Facade { /// * `lifetime` - The duration in seconds for the new key. The key will be /// no longer valid after `lifetime` seconds. pub async fn generate_auth_key(&self, lifetime: Option) -> Result { - let auth_key = key::generate_key(lifetime); + let peer_key = key::generate_key(lifetime); + + self.db_key_repository.add(&peer_key)?; - self.db_key_repository.add(&auth_key)?; + self.in_memory_key_repository.insert(&peer_key).await; - self.keys.write().await.insert(auth_key.key.clone(), auth_key.clone()); - Ok(auth_key) + Ok(peer_key) } /// It adds a pre-generated permanent authentication key. @@ -250,15 +252,16 @@ impl Facade { key: Key, valid_until: Option, ) -> Result { - let auth_key = PeerKey { key, valid_until }; + let peer_key = PeerKey { key, valid_until }; // code-review: should we return a friendly error instead of the DB // constrain error when the key already exist? For now, it's returning // the specif error for each DB driver when a UNIQUE constrain fails. - self.db_key_repository.add(&auth_key)?; + self.db_key_repository.add(&peer_key)?; - self.keys.write().await.insert(auth_key.key.clone(), auth_key.clone()); - Ok(auth_key) + self.in_memory_key_repository.insert(&peer_key).await; + + Ok(peer_key) } /// It removes an authentication key. @@ -280,7 +283,7 @@ impl Facade { /// /// # Context: Authentication pub async fn remove_in_memory_auth_key(&self, key: &Key) { - self.keys.write().await.remove(key); + self.in_memory_key_repository.remove(key).await; } /// The `Tracker` stores the authentication keys in memory and in the database. @@ -296,12 +299,10 @@ impl Facade { pub async fn load_keys_from_database(&self) -> Result<(), databases::error::Error> { let keys_from_database = self.db_key_repository.load_keys()?; - let mut keys = self.keys.write().await; - - keys.clear(); + self.in_memory_key_repository.clear().await; for key in keys_from_database { - keys.insert(key.key.clone(), key); + self.in_memory_key_repository.insert(&key).await; } Ok(()) From a93a79c5a6bdf63d37ac273a3f23c98b3f4e0801 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 17:34:51 +0000 Subject: [PATCH 04/18] refactor: [#1195] remove deprecated context section in docs It was used to group methods by services in the old core tracker. --- src/core/authentication/mod.rs | 18 ------------------ 1 file changed, 18 deletions(-) diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 4a65a26a7..1b841767e 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -60,8 +60,6 @@ impl Facade { /// # Errors /// /// Will return an error if the the authentication key cannot be verified. - /// - /// # Context: Authentication pub async fn authenticate(&self, key: &Key) -> Result<(), Error> { if self.is_private() { self.verify_auth_key(key).await @@ -77,8 +75,6 @@ impl Facade { /// It verifies an authentication key. /// - /// # Context: Authentication - /// /// # Errors /// /// Will return a `key::Error` if unable to get any `auth_key`. @@ -180,8 +176,6 @@ impl Facade { /// /// Authentication keys are used by HTTP trackers. /// - /// # Context: Authentication - /// /// # Errors /// /// Will return a `database::Error` if unable to add the `auth_key` to the database. @@ -193,8 +187,6 @@ impl Facade { /// /// Authentication keys are used by HTTP trackers. /// - /// # Context: Authentication - /// /// # Errors /// /// Will return a `database::Error` if unable to add the `auth_key` to the database. @@ -217,8 +209,6 @@ impl Facade { /// /// Authentication keys are used by HTTP trackers. /// - /// # Context: Authentication - /// /// # Errors /// /// Will return a `database::Error` if unable to add the `auth_key` to the @@ -235,8 +225,6 @@ impl Facade { /// /// Authentication keys are used by HTTP trackers. /// - /// # Context: Authentication - /// /// # Errors /// /// Will return a `database::Error` if unable to add the `auth_key` to the @@ -266,8 +254,6 @@ impl Facade { /// It removes an authentication key. /// - /// # Context: Authentication - /// /// # Errors /// /// Will return a `database::Error` if unable to remove the `key` to the database. @@ -280,8 +266,6 @@ impl Facade { } /// It removes an authentication key from memory. - /// - /// # Context: Authentication pub async fn remove_in_memory_auth_key(&self, key: &Key) { self.in_memory_key_repository.remove(key).await; } @@ -291,8 +275,6 @@ impl Facade { /// into memory with this function. Keys are automatically stored in the database when they /// are generated. /// - /// # Context: Authentication - /// /// # Errors /// /// Will return a `database::Error` if unable to `load_keys` from the database. From cd542dc3523ce52a26e32961f222f5f4167dd63f Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 17:53:55 +0000 Subject: [PATCH 05/18] refactor: [#1195] extract authentication::Service --- src/core/authentication/mod.rs | 69 +++++++++++------------------ src/core/authentication/service.rs | 70 ++++++++++++++++++++++++++++++ 2 files changed, 95 insertions(+), 44 deletions(-) create mode 100644 src/core/authentication/service.rs diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 1b841767e..7e60648f5 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -1,4 +1,3 @@ -use std::panic::Location; use std::sync::Arc; use std::time::Duration; @@ -14,6 +13,7 @@ use super::error::PeerKeyError; use crate::CurrentClock; pub mod key; +pub mod service; pub type PeerKey = key::PeerKey; pub type Key = key::Key; @@ -34,23 +34,25 @@ pub struct AddKeyRequest { } pub struct Facade { - /// The tracker configuration. - config: Core, - /// The database repository for the authentication keys. db_key_repository: DatabaseKeyRepository, /// In-memory implementation of the authentication key repository. - in_memory_key_repository: InMemoryKeyRepository, + in_memory_key_repository: Arc, + + /// The authentication service. + authentication_service: service::Service, } impl Facade { #[must_use] pub fn new(config: &Core, database: &Arc>) -> Self { + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + Self { - config: config.clone(), db_key_repository: DatabaseKeyRepository::new(database), - in_memory_key_repository: InMemoryKeyRepository::default(), + in_memory_key_repository: in_memory_key_repository.clone(), + authentication_service: service::Service::new(config, &in_memory_key_repository), } } @@ -61,40 +63,7 @@ impl Facade { /// /// Will return an error if the the authentication key cannot be verified. pub async fn authenticate(&self, key: &Key) -> Result<(), Error> { - if self.is_private() { - self.verify_auth_key(key).await - } else { - Ok(()) - } - } - - /// Returns `true` is the tracker is in private mode. - pub fn is_private(&self) -> bool { - self.config.private - } - - /// It verifies an authentication key. - /// - /// # Errors - /// - /// Will return a `key::Error` if unable to get any `auth_key`. - pub async fn verify_auth_key(&self, key: &Key) -> Result<(), Error> { - match self.in_memory_key_repository.get(key).await { - None => Err(Error::UnableToReadKey { - location: Location::caller(), - key: Box::new(key.clone()), - }), - Some(key) => match self.config.private_mode { - Some(private_mode) => { - if private_mode.check_keys_expiration { - return key::verify_key_expiration(&key); - } - - Ok(()) - } - None => key::verify_key_expiration(&key), - }, - } + self.authentication_service.authenticate(key).await } /// Adds new peer keys to the tracker. @@ -340,7 +309,11 @@ mod tests { let unregistered_key = authentication::Key::from_str("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap(); - assert!(authentication.verify_auth_key(&unregistered_key).await.is_err()); + assert!(authentication + .authentication_service + .verify_auth_key(&unregistered_key) + .await + .is_err()); } #[tokio::test] @@ -355,7 +328,11 @@ mod tests { let result = authentication.remove_auth_key(&expiring_key.key()).await; assert!(result.is_ok()); - assert!(authentication.verify_auth_key(&expiring_key.key()).await.is_err()); + assert!(authentication + .authentication_service + .verify_auth_key(&expiring_key.key()) + .await + .is_err()); } #[tokio::test] @@ -373,7 +350,11 @@ mod tests { let result = authentication.load_keys_from_database().await; assert!(result.is_ok()); - assert!(authentication.verify_auth_key(&expiring_key.key()).await.is_ok()); + assert!(authentication + .authentication_service + .verify_auth_key(&expiring_key.key()) + .await + .is_ok()); } mod with_expiring_and { diff --git a/src/core/authentication/service.rs b/src/core/authentication/service.rs new file mode 100644 index 000000000..d33ed673b --- /dev/null +++ b/src/core/authentication/service.rs @@ -0,0 +1,70 @@ +use std::panic::Location; +use std::sync::Arc; + +use torrust_tracker_configuration::Core; + +use super::key::repository::in_memory::InMemoryKeyRepository; +use super::{key, Error, Key}; + +#[derive(Debug)] +pub struct Service { + /// The tracker configuration. + config: Core, + + /// In-memory implementation of the authentication key repository. + in_memory_key_repository: Arc, +} + +impl Service { + #[must_use] + pub fn new(config: &Core, in_memory_key_repository: &Arc) -> Self { + Self { + config: config.clone(), + in_memory_key_repository: in_memory_key_repository.clone(), + } + } + + /// It authenticates the peer `key` against the `Tracker` authentication + /// key list. + /// + /// # Errors + /// + /// Will return an error if the the authentication key cannot be verified. + pub async fn authenticate(&self, key: &Key) -> Result<(), Error> { + if self.is_private() { + self.verify_auth_key(key).await + } else { + Ok(()) + } + } + + /// Returns `true` is the tracker is in private mode. + #[must_use] + pub fn is_private(&self) -> bool { + self.config.private + } + + /// It verifies an authentication key. + /// + /// # Errors + /// + /// Will return a `key::Error` if unable to get any `auth_key`. + pub async fn verify_auth_key(&self, key: &Key) -> Result<(), Error> { + match self.in_memory_key_repository.get(key).await { + None => Err(Error::UnableToReadKey { + location: Location::caller(), + key: Box::new(key.clone()), + }), + Some(key) => match self.config.private_mode { + Some(private_mode) => { + if private_mode.check_keys_expiration { + return key::verify_key_expiration(&key); + } + + Ok(()) + } + None => key::verify_key_expiration(&key), + }, + } + } +} From 81b4b3c0a006378264c2248a9b188d45e0783246 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 18:00:35 +0000 Subject: [PATCH 06/18] refactor: [#1195] extract and move method --- .../authentication/key/repository/in_memory.rs | 11 +++++++++++ src/core/authentication/mod.rs | 14 +++++--------- 2 files changed, 16 insertions(+), 9 deletions(-) diff --git a/src/core/authentication/key/repository/in_memory.rs b/src/core/authentication/key/repository/in_memory.rs index 266d5a5fb..a15f9ecfa 100644 --- a/src/core/authentication/key/repository/in_memory.rs +++ b/src/core/authentication/key/repository/in_memory.rs @@ -27,4 +27,15 @@ impl InMemoryKeyRepository { let mut keys = self.keys.write().await; keys.clear(); } + + /// It resets the authentication keys with a new list of keys. + pub async fn reset_with(&self, peer_keys: Vec) { + let mut keys_lock = self.keys.write().await; + + keys_lock.clear(); + + for key in peer_keys { + keys_lock.insert(key.key.clone(), key.clone()); + } + } } diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 7e60648f5..9d47409e3 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -239,10 +239,10 @@ impl Facade { self.in_memory_key_repository.remove(key).await; } - /// The `Tracker` stores the authentication keys in memory and in the database. - /// In case you need to restart the `Tracker` you can load the keys from the database - /// into memory with this function. Keys are automatically stored in the database when they - /// are generated. + /// The `Tracker` stores the authentication keys in memory and in the + /// database. In case you need to restart the `Tracker` you can load the + /// keys from the database into memory with this function. Keys are + /// automatically stored in the database when they are generated. /// /// # Errors /// @@ -250,11 +250,7 @@ impl Facade { pub async fn load_keys_from_database(&self) -> Result<(), databases::error::Error> { let keys_from_database = self.db_key_repository.load_keys()?; - self.in_memory_key_repository.clear().await; - - for key in keys_from_database { - self.in_memory_key_repository.insert(&key).await; - } + self.in_memory_key_repository.reset_with(keys_from_database).await; Ok(()) } From 23590e7bff89f842682209f0801b20ff37ebd98f Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 18:08:06 +0000 Subject: [PATCH 07/18] refactor: [#1195] make method private --- src/core/authentication/mod.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 9d47409e3..098524ed9 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -186,7 +186,7 @@ impl Facade { /// # Arguments /// /// * `key` - The pre-generated key. - pub async fn add_permanent_auth_key(&self, key: Key) -> Result { + async fn add_permanent_auth_key(&self, key: Key) -> Result { self.add_auth_key(key, None).await } @@ -239,9 +239,9 @@ impl Facade { self.in_memory_key_repository.remove(key).await; } - /// The `Tracker` stores the authentication keys in memory and in the - /// database. In case you need to restart the `Tracker` you can load the - /// keys from the database into memory with this function. Keys are + /// The `Tracker` stores the authentication keys in memory and in the + /// database. In case you need to restart the `Tracker` you can load the + /// keys from the database into memory with this function. Keys are /// automatically stored in the database when they are generated. /// /// # Errors From bb2f9e07072af8b58330ef9842d1b99434437ae9 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Tue, 21 Jan 2025 18:28:31 +0000 Subject: [PATCH 08/18] refactor: [#1195] extract core::authentication::handler::KeysHandler --- src/core/authentication/handler.rs | 233 ++++++++++++++++++ src/core/authentication/mod.rs | 144 ++--------- .../apis/v1/context/auth_key/handlers.rs | 3 +- 3 files changed, 249 insertions(+), 131 deletions(-) create mode 100644 src/core/authentication/handler.rs diff --git a/src/core/authentication/handler.rs b/src/core/authentication/handler.rs new file mode 100644 index 000000000..f327c4fdd --- /dev/null +++ b/src/core/authentication/handler.rs @@ -0,0 +1,233 @@ +use std::sync::Arc; +use std::time::Duration; + +use torrust_tracker_clock::clock::Time; +use torrust_tracker_located_error::Located; +use torrust_tracker_primitives::DurationSinceUnixEpoch; + +use super::key::repository::in_memory::InMemoryKeyRepository; +use super::key::repository::persisted::DatabaseKeyRepository; +use super::{key, CurrentClock, Key, PeerKey}; +use crate::core::databases; +use crate::core::error::PeerKeyError; + +/// This type contains the info needed to add a new tracker key. +/// +/// You can upload a pre-generated key or let the app to generate a new one. +/// You can also set an expiration date or leave it empty (`None`) if you want +/// to create a permanent key that does not expire. +#[derive(Debug)] +pub struct AddKeyRequest { + /// The pre-generated key. Use `None` to generate a random key. + pub opt_key: Option, + + /// How long the key will be valid in seconds. Use `None` for permanent keys. + pub opt_seconds_valid: Option, +} + +pub struct KeysHandler { + /// The database repository for the authentication keys. + db_key_repository: Arc, + + /// In-memory implementation of the authentication key repository. + in_memory_key_repository: Arc, +} + +impl KeysHandler { + #[must_use] + pub fn new(db_key_repository: &Arc, in_memory_key_repository: &Arc) -> Self { + Self { + db_key_repository: db_key_repository.clone(), + in_memory_key_repository: in_memory_key_repository.clone(), + } + } + + /// Adds new peer keys to the tracker. + /// + /// Keys can be pre-generated or randomly created. They can also be permanent or expire. + /// + /// # Errors + /// + /// Will return an error if: + /// + /// - The key duration overflows the duration type maximum value. + /// - The provided pre-generated key is invalid. + /// - The key could not been persisted due to database issues. + pub async fn add_peer_key(&self, add_key_req: AddKeyRequest) -> Result { + // code-review: all methods related to keys should be moved to a new independent "keys" service. + + match add_key_req.opt_key { + // Upload pre-generated key + Some(pre_existing_key) => { + if let Some(seconds_valid) = add_key_req.opt_seconds_valid { + // Expiring key + let Some(valid_until) = CurrentClock::now_add(&Duration::from_secs(seconds_valid)) else { + return Err(PeerKeyError::DurationOverflow { seconds_valid }); + }; + + let key = pre_existing_key.parse::(); + + match key { + Ok(key) => match self.add_auth_key(key, Some(valid_until)).await { + Ok(auth_key) => Ok(auth_key), + Err(err) => Err(PeerKeyError::DatabaseError { + source: Located(err).into(), + }), + }, + Err(err) => Err(PeerKeyError::InvalidKey { + key: pre_existing_key, + source: Located(err).into(), + }), + } + } else { + // Permanent key + let key = pre_existing_key.parse::(); + + match key { + Ok(key) => match self.add_permanent_auth_key(key).await { + Ok(auth_key) => Ok(auth_key), + Err(err) => Err(PeerKeyError::DatabaseError { + source: Located(err).into(), + }), + }, + Err(err) => Err(PeerKeyError::InvalidKey { + key: pre_existing_key, + source: Located(err).into(), + }), + } + } + } + // Generate a new random key + None => match add_key_req.opt_seconds_valid { + // Expiring key + Some(seconds_valid) => match self.generate_auth_key(Some(Duration::from_secs(seconds_valid))).await { + Ok(auth_key) => Ok(auth_key), + Err(err) => Err(PeerKeyError::DatabaseError { + source: Located(err).into(), + }), + }, + // Permanent key + None => match self.generate_permanent_auth_key().await { + Ok(auth_key) => Ok(auth_key), + Err(err) => Err(PeerKeyError::DatabaseError { + source: Located(err).into(), + }), + }, + }, + } + } + + /// It generates a new permanent authentication key. + /// + /// Authentication keys are used by HTTP trackers. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to add the `auth_key` to the database. + pub async fn generate_permanent_auth_key(&self) -> Result { + self.generate_auth_key(None).await + } + + /// It generates a new expiring authentication key. + /// + /// Authentication keys are used by HTTP trackers. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to add the `auth_key` to the database. + /// + /// # Arguments + /// + /// * `lifetime` - The duration in seconds for the new key. The key will be + /// no longer valid after `lifetime` seconds. + pub async fn generate_auth_key(&self, lifetime: Option) -> Result { + let peer_key = key::generate_key(lifetime); + + self.db_key_repository.add(&peer_key)?; + + self.in_memory_key_repository.insert(&peer_key).await; + + Ok(peer_key) + } + + /// It adds a pre-generated permanent authentication key. + /// + /// Authentication keys are used by HTTP trackers. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to add the `auth_key` to the + /// database. For example, if the key already exist. + /// + /// # Arguments + /// + /// * `key` - The pre-generated key. + pub async fn add_permanent_auth_key(&self, key: Key) -> Result { + self.add_auth_key(key, None).await + } + + /// It adds a pre-generated authentication key. + /// + /// Authentication keys are used by HTTP trackers. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to add the `auth_key` to the + /// database. For example, if the key already exist. + /// + /// # Arguments + /// + /// * `key` - The pre-generated key. + /// * `lifetime` - The duration in seconds for the new key. The key will be + /// no longer valid after `lifetime` seconds. + pub async fn add_auth_key( + &self, + key: Key, + valid_until: Option, + ) -> Result { + let peer_key = PeerKey { key, valid_until }; + + // code-review: should we return a friendly error instead of the DB + // constrain error when the key already exist? For now, it's returning + // the specif error for each DB driver when a UNIQUE constrain fails. + self.db_key_repository.add(&peer_key)?; + + self.in_memory_key_repository.insert(&peer_key).await; + + Ok(peer_key) + } + + /// It removes an authentication key. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to remove the `key` to the database. + pub async fn remove_auth_key(&self, key: &Key) -> Result<(), databases::error::Error> { + self.db_key_repository.remove(key)?; + + self.remove_in_memory_auth_key(key).await; + + Ok(()) + } + + /// It removes an authentication key from memory. + pub async fn remove_in_memory_auth_key(&self, key: &Key) { + self.in_memory_key_repository.remove(key).await; + } + + /// The `Tracker` stores the authentication keys in memory and in the + /// database. In case you need to restart the `Tracker` you can load the + /// keys from the database into memory with this function. Keys are + /// automatically stored in the database when they are generated. + /// + /// # Errors + /// + /// Will return a `database::Error` if unable to `load_keys` from the database. + pub async fn load_keys_from_database(&self) -> Result<(), databases::error::Error> { + let keys_from_database = self.db_key_repository.load_keys()?; + + self.in_memory_key_repository.reset_with(keys_from_database).await; + + Ok(()) + } +} diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 098524ed9..5c9356c10 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -1,17 +1,17 @@ use std::sync::Arc; use std::time::Duration; +use handler::{AddKeyRequest, KeysHandler}; use key::repository::in_memory::InMemoryKeyRepository; use key::repository::persisted::DatabaseKeyRepository; -use torrust_tracker_clock::clock::Time; use torrust_tracker_configuration::Core; -use torrust_tracker_located_error::Located; use torrust_tracker_primitives::DurationSinceUnixEpoch; use super::databases::{self, Database}; use super::error::PeerKeyError; use crate::CurrentClock; +pub mod handler; pub mod key; pub mod service; @@ -19,40 +19,23 @@ pub type PeerKey = key::PeerKey; pub type Key = key::Key; pub type Error = key::Error; -/// This type contains the info needed to add a new tracker key. -/// -/// You can upload a pre-generated key or let the app to generate a new one. -/// You can also set an expiration date or leave it empty (`None`) if you want -/// to create a permanent key that does not expire. -#[derive(Debug)] -pub struct AddKeyRequest { - /// The pre-generated key. Use `None` to generate a random key. - pub opt_key: Option, - - /// How long the key will be valid in seconds. Use `None` for permanent keys. - pub opt_seconds_valid: Option, -} - pub struct Facade { - /// The database repository for the authentication keys. - db_key_repository: DatabaseKeyRepository, - - /// In-memory implementation of the authentication key repository. - in_memory_key_repository: Arc, - /// The authentication service. authentication_service: service::Service, + + /// The keys handler. + keys_handler: handler::KeysHandler, } impl Facade { #[must_use] pub fn new(config: &Core, database: &Arc>) -> Self { + let db_key_repository = Arc::new(DatabaseKeyRepository::new(database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); Self { - db_key_repository: DatabaseKeyRepository::new(database), - in_memory_key_repository: in_memory_key_repository.clone(), authentication_service: service::Service::new(config, &in_memory_key_repository), + keys_handler: KeysHandler::new(&db_key_repository.clone(), &in_memory_key_repository.clone()), } } @@ -78,67 +61,7 @@ impl Facade { /// - The provided pre-generated key is invalid. /// - The key could not been persisted due to database issues. pub async fn add_peer_key(&self, add_key_req: AddKeyRequest) -> Result { - // code-review: all methods related to keys should be moved to a new independent "keys" service. - - match add_key_req.opt_key { - // Upload pre-generated key - Some(pre_existing_key) => { - if let Some(seconds_valid) = add_key_req.opt_seconds_valid { - // Expiring key - let Some(valid_until) = CurrentClock::now_add(&Duration::from_secs(seconds_valid)) else { - return Err(PeerKeyError::DurationOverflow { seconds_valid }); - }; - - let key = pre_existing_key.parse::(); - - match key { - Ok(key) => match self.add_auth_key(key, Some(valid_until)).await { - Ok(auth_key) => Ok(auth_key), - Err(err) => Err(PeerKeyError::DatabaseError { - source: Located(err).into(), - }), - }, - Err(err) => Err(PeerKeyError::InvalidKey { - key: pre_existing_key, - source: Located(err).into(), - }), - } - } else { - // Permanent key - let key = pre_existing_key.parse::(); - - match key { - Ok(key) => match self.add_permanent_auth_key(key).await { - Ok(auth_key) => Ok(auth_key), - Err(err) => Err(PeerKeyError::DatabaseError { - source: Located(err).into(), - }), - }, - Err(err) => Err(PeerKeyError::InvalidKey { - key: pre_existing_key, - source: Located(err).into(), - }), - } - } - } - // Generate a new random key - None => match add_key_req.opt_seconds_valid { - // Expiring key - Some(seconds_valid) => match self.generate_auth_key(Some(Duration::from_secs(seconds_valid))).await { - Ok(auth_key) => Ok(auth_key), - Err(err) => Err(PeerKeyError::DatabaseError { - source: Located(err).into(), - }), - }, - // Permanent key - None => match self.generate_permanent_auth_key().await { - Ok(auth_key) => Ok(auth_key), - Err(err) => Err(PeerKeyError::DatabaseError { - source: Located(err).into(), - }), - }, - }, - } + self.keys_handler.add_peer_key(add_key_req).await } /// It generates a new permanent authentication key. @@ -149,7 +72,7 @@ impl Facade { /// /// Will return a `database::Error` if unable to add the `auth_key` to the database. pub async fn generate_permanent_auth_key(&self) -> Result { - self.generate_auth_key(None).await + self.keys_handler.generate_permanent_auth_key().await } /// It generates a new expiring authentication key. @@ -165,29 +88,7 @@ impl Facade { /// * `lifetime` - The duration in seconds for the new key. The key will be /// no longer valid after `lifetime` seconds. pub async fn generate_auth_key(&self, lifetime: Option) -> Result { - let peer_key = key::generate_key(lifetime); - - self.db_key_repository.add(&peer_key)?; - - self.in_memory_key_repository.insert(&peer_key).await; - - Ok(peer_key) - } - - /// It adds a pre-generated permanent authentication key. - /// - /// Authentication keys are used by HTTP trackers. - /// - /// # Errors - /// - /// Will return a `database::Error` if unable to add the `auth_key` to the - /// database. For example, if the key already exist. - /// - /// # Arguments - /// - /// * `key` - The pre-generated key. - async fn add_permanent_auth_key(&self, key: Key) -> Result { - self.add_auth_key(key, None).await + self.keys_handler.generate_auth_key(lifetime).await } /// It adds a pre-generated authentication key. @@ -209,16 +110,7 @@ impl Facade { key: Key, valid_until: Option, ) -> Result { - let peer_key = PeerKey { key, valid_until }; - - // code-review: should we return a friendly error instead of the DB - // constrain error when the key already exist? For now, it's returning - // the specif error for each DB driver when a UNIQUE constrain fails. - self.db_key_repository.add(&peer_key)?; - - self.in_memory_key_repository.insert(&peer_key).await; - - Ok(peer_key) + self.keys_handler.add_auth_key(key, valid_until).await } /// It removes an authentication key. @@ -227,16 +119,12 @@ impl Facade { /// /// Will return a `database::Error` if unable to remove the `key` to the database. pub async fn remove_auth_key(&self, key: &Key) -> Result<(), databases::error::Error> { - self.db_key_repository.remove(key)?; - - self.remove_in_memory_auth_key(key).await; - - Ok(()) + self.keys_handler.remove_auth_key(key).await } /// It removes an authentication key from memory. pub async fn remove_in_memory_auth_key(&self, key: &Key) { - self.in_memory_key_repository.remove(key).await; + self.keys_handler.remove_in_memory_auth_key(key).await; } /// The `Tracker` stores the authentication keys in memory and in the @@ -248,11 +136,7 @@ impl Facade { /// /// Will return a `database::Error` if unable to `load_keys` from the database. pub async fn load_keys_from_database(&self) -> Result<(), databases::error::Error> { - let keys_from_database = self.db_key_repository.load_keys()?; - - self.in_memory_key_repository.reset_with(keys_from_database).await; - - Ok(()) + self.keys_handler.load_keys_from_database().await } } diff --git a/src/servers/apis/v1/context/auth_key/handlers.rs b/src/servers/apis/v1/context/auth_key/handlers.rs index ba345d8a5..f0c131bbf 100644 --- a/src/servers/apis/v1/context/auth_key/handlers.rs +++ b/src/servers/apis/v1/context/auth_key/handlers.rs @@ -12,7 +12,8 @@ use super::responses::{ auth_key_response, failed_to_delete_key_response, failed_to_generate_key_response, failed_to_reload_keys_response, invalid_auth_key_duration_response, invalid_auth_key_response, }; -use crate::core::authentication::{AddKeyRequest, Key}; +use crate::core::authentication::handler::AddKeyRequest; +use crate::core::authentication::Key; use crate::core::Tracker; use crate::servers::apis::v1::context::auth_key::resources::AuthKey; use crate::servers::apis::v1::responses::{invalid_auth_key_param_response, ok_response}; From c06da07c44300ced5fe28976119b4386a68d369b Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 08:09:42 +0000 Subject: [PATCH 09/18] refactor: [#1195] more authentication tests to authentication service --- src/core/authentication/mod.rs | 33 +++++--------------------- src/core/authentication/service.rs | 37 +++++++++++++++++++++++++++++- 2 files changed, 42 insertions(+), 28 deletions(-) diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 5c9356c10..86337b714 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -145,7 +145,6 @@ mod tests { mod the_tracker_configured_as_private { - use std::str::FromStr; use std::time::Duration; use torrust_tracker_configuration::v2_0_0::core::PrivateMode; @@ -172,30 +171,6 @@ mod tests { authentication::Facade::new(&config.core, &database.clone()) } - #[tokio::test] - async fn it_should_fail_authenticating_a_peer_when_it_uses_an_unregistered_key() { - let authentication = instantiate_authentication(); - - let unregistered_key = authentication::Key::from_str("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap(); - - let result = authentication.authenticate(&unregistered_key).await; - - assert!(result.is_err()); - } - - #[tokio::test] - async fn it_should_fail_verifying_an_unregistered_authentication_key() { - let authentication = instantiate_authentication(); - - let unregistered_key = authentication::Key::from_str("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap(); - - assert!(authentication - .authentication_service - .verify_auth_key(&unregistered_key) - .await - .is_err()); - } - #[tokio::test] async fn it_should_remove_an_authentication_key() { let authentication = instantiate_authentication(); @@ -208,9 +183,11 @@ mod tests { let result = authentication.remove_auth_key(&expiring_key.key()).await; assert!(result.is_ok()); + + // The key should no longer be valid assert!(authentication .authentication_service - .verify_auth_key(&expiring_key.key()) + .authenticate(&expiring_key.key()) .await .is_err()); } @@ -230,9 +207,11 @@ mod tests { let result = authentication.load_keys_from_database().await; assert!(result.is_ok()); + + // The key should no longer be valid assert!(authentication .authentication_service - .verify_auth_key(&expiring_key.key()) + .authenticate(&expiring_key.key()) .await .is_ok()); } diff --git a/src/core/authentication/service.rs b/src/core/authentication/service.rs index d33ed673b..d7572136f 100644 --- a/src/core/authentication/service.rs +++ b/src/core/authentication/service.rs @@ -49,7 +49,7 @@ impl Service { /// # Errors /// /// Will return a `key::Error` if unable to get any `auth_key`. - pub async fn verify_auth_key(&self, key: &Key) -> Result<(), Error> { + async fn verify_auth_key(&self, key: &Key) -> Result<(), Error> { match self.in_memory_key_repository.get(key).await { None => Err(Error::UnableToReadKey { location: Location::caller(), @@ -68,3 +68,38 @@ impl Service { } } } + +#[cfg(test)] +mod tests { + + mod the_tracker_configured_as_private { + + use std::str::FromStr; + use std::sync::Arc; + + use torrust_tracker_test_helpers::configuration; + + use crate::core::authentication; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::service::Service; + + fn instantiate_authentication() -> Service { + let config = configuration::ephemeral_private(); + + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + + Service::new(&config.core, &in_memory_key_repository.clone()) + } + + #[tokio::test] + async fn it_should_not_authenticate_an_unregistered_key() { + let authentication = instantiate_authentication(); + + let unregistered_key = authentication::Key::from_str("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap(); + + let result = authentication.authenticate(&unregistered_key).await; + + assert!(result.is_err()); + } + } +} From 9c61b2685d0d0ffbba7be78ba032232f4e654931 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 08:26:06 +0000 Subject: [PATCH 10/18] refactor: [#1195] move tests to KeysHandler These tests do not require the authentication service. --- src/core/authentication/handler.rs | 133 +++++++++++++++++++++++++++++ src/core/authentication/mod.rs | 64 -------------- 2 files changed, 133 insertions(+), 64 deletions(-) diff --git a/src/core/authentication/handler.rs b/src/core/authentication/handler.rs index f327c4fdd..3ada2b110 100644 --- a/src/core/authentication/handler.rs +++ b/src/core/authentication/handler.rs @@ -231,3 +231,136 @@ impl KeysHandler { Ok(()) } } + +#[cfg(test)] +mod tests { + + mod the_keys_handler_when_tracker_is_configured_as_private { + + use std::sync::Arc; + + use torrust_tracker_configuration::v2_0_0::core::PrivateMode; + use torrust_tracker_configuration::Configuration; + use torrust_tracker_test_helpers::configuration; + + use crate::core::authentication::handler::KeysHandler; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::services::initialize_database; + + fn instantiate_keys_handler() -> KeysHandler { + let config = configuration::ephemeral_private(); + + instantiate_keys_handler_with_configuration(&config) + } + + #[allow(dead_code)] + fn instantiate_keys_handler_with_checking_keys_expiration_disabled() -> KeysHandler { + let mut config = configuration::ephemeral_private(); + + config.core.private_mode = Some(PrivateMode { + check_keys_expiration: false, + }); + + instantiate_keys_handler_with_configuration(&config) + } + + fn instantiate_keys_handler_with_configuration(config: &Configuration) -> KeysHandler { + let database = initialize_database(config); + + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + + KeysHandler::new(&db_key_repository, &in_memory_key_repository) + } + + mod with_expiring_and { + + mod randomly_generated_keys { + use std::time::Duration; + + use torrust_tracker_clock::clock::Time; + + use crate::core::authentication::handler::tests::the_keys_handler_when_tracker_is_configured_as_private::instantiate_keys_handler; + use crate::CurrentClock; + + #[tokio::test] + async fn it_should_generate_the_key() { + let keys_handler = instantiate_keys_handler(); + + let peer_key = keys_handler.generate_auth_key(Some(Duration::from_secs(100))).await.unwrap(); + + assert_eq!( + peer_key.valid_until, + Some(CurrentClock::now_add(&Duration::from_secs(100)).unwrap()) + ); + } + } + + mod pre_generated_keys { + use std::time::Duration; + + use torrust_tracker_clock::clock::Time; + + use crate::core::authentication::handler::tests::the_keys_handler_when_tracker_is_configured_as_private::instantiate_keys_handler; + use crate::core::authentication::{AddKeyRequest, Key}; + use crate::CurrentClock; + + #[tokio::test] + async fn it_should_add_a_pre_generated_key() { + let keys_handler = instantiate_keys_handler(); + + let peer_key = keys_handler + .add_peer_key(AddKeyRequest { + opt_key: Some(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap().to_string()), + opt_seconds_valid: Some(100), + }) + .await + .unwrap(); + + assert_eq!( + peer_key.valid_until, + Some(CurrentClock::now_add(&Duration::from_secs(100)).unwrap()) + ); + } + } + } + + mod with_permanent_and { + + mod randomly_generated_keys { + use crate::core::authentication::handler::tests::the_keys_handler_when_tracker_is_configured_as_private::instantiate_keys_handler; + + #[tokio::test] + async fn it_should_generate_the_key() { + let keys_handler = instantiate_keys_handler(); + + let peer_key = keys_handler.generate_permanent_auth_key().await.unwrap(); + + assert_eq!(peer_key.valid_until, None); + } + } + + mod pre_generated_keys { + + use crate::core::authentication::handler::tests::the_keys_handler_when_tracker_is_configured_as_private::instantiate_keys_handler; + use crate::core::authentication::{AddKeyRequest, Key}; + + #[tokio::test] + async fn it_should_add_a_pre_generated_key() { + let keys_handler = instantiate_keys_handler(); + + let peer_key = keys_handler + .add_peer_key(AddKeyRequest { + opt_key: Some(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap().to_string()), + opt_seconds_valid: None, + }) + .await + .unwrap(); + + assert_eq!(peer_key.valid_until, None); + } + } + } + } +} diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 86337b714..4d0001fd2 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -221,28 +221,10 @@ mod tests { mod randomly_generated_keys { use std::time::Duration; - use torrust_tracker_clock::clock::Time; - use crate::core::authentication::tests::the_tracker_configured_as_private::{ instantiate_authentication, instantiate_authentication_with_checking_keys_expiration_disabled, }; use crate::core::authentication::Key; - use crate::CurrentClock; - - #[tokio::test] - async fn it_should_generate_the_key() { - let authentication = instantiate_authentication(); - - let peer_key = authentication - .generate_auth_key(Some(Duration::from_secs(100))) - .await - .unwrap(); - - assert_eq!( - peer_key.valid_until, - Some(CurrentClock::now_add(&Duration::from_secs(100)).unwrap()) - ); - } #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { @@ -274,33 +256,11 @@ mod tests { } mod pre_generated_keys { - use std::time::Duration; - - use torrust_tracker_clock::clock::Time; use crate::core::authentication::tests::the_tracker_configured_as_private::{ instantiate_authentication, instantiate_authentication_with_checking_keys_expiration_disabled, }; use crate::core::authentication::{AddKeyRequest, Key}; - use crate::CurrentClock; - - #[tokio::test] - async fn it_should_add_a_pre_generated_key() { - let authentication = instantiate_authentication(); - - let peer_key = authentication - .add_peer_key(AddKeyRequest { - opt_key: Some(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap().to_string()), - opt_seconds_valid: Some(100), - }) - .await - .unwrap(); - - assert_eq!( - peer_key.valid_until, - Some(CurrentClock::now_add(&Duration::from_secs(100)).unwrap()) - ); - } #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { @@ -341,15 +301,6 @@ mod tests { mod randomly_generated_keys { use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication; - #[tokio::test] - async fn it_should_generate_the_key() { - let authentication = instantiate_authentication(); - - let peer_key = authentication.generate_permanent_auth_key().await.unwrap(); - - assert_eq!(peer_key.valid_until, None); - } - #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { let authentication = instantiate_authentication(); @@ -366,21 +317,6 @@ mod tests { use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication; use crate::core::authentication::{AddKeyRequest, Key}; - #[tokio::test] - async fn it_should_add_a_pre_generated_key() { - let authentication = instantiate_authentication(); - - let peer_key = authentication - .add_peer_key(AddKeyRequest { - opt_key: Some(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap().to_string()), - opt_seconds_valid: None, - }) - .await - .unwrap(); - - assert_eq!(peer_key.valid_until, None); - } - #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { let authentication = instantiate_authentication(); From 663250bfa5921fd9e4ab949bd4af582fc1dfa771 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 08:29:39 +0000 Subject: [PATCH 11/18] refactor: [#1195] rename methods --- src/core/authentication/mod.rs | 30 ++++++++++++++++-------------- 1 file changed, 16 insertions(+), 14 deletions(-) diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 4d0001fd2..bab0de8a3 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -153,14 +153,15 @@ mod tests { use crate::core::authentication; use crate::core::services::initialize_database; - fn instantiate_authentication() -> authentication::Facade { + fn instantiate_authentication_facade() -> authentication::Facade { let config = configuration::ephemeral_private(); let database = initialize_database(&config); + authentication::Facade::new(&config.core, &database.clone()) } - fn instantiate_authentication_with_checking_keys_expiration_disabled() -> authentication::Facade { + fn instantiate_authentication_facade_with_checking_keys_expiration_disabled() -> authentication::Facade { let mut config = configuration::ephemeral_private(); config.core.private_mode = Some(PrivateMode { @@ -168,12 +169,13 @@ mod tests { }); let database = initialize_database(&config); + authentication::Facade::new(&config.core, &database.clone()) } #[tokio::test] async fn it_should_remove_an_authentication_key() { - let authentication = instantiate_authentication(); + let authentication = instantiate_authentication_facade(); let expiring_key = authentication .generate_auth_key(Some(Duration::from_secs(100))) @@ -194,7 +196,7 @@ mod tests { #[tokio::test] async fn it_should_load_authentication_keys_from_the_database() { - let authentication = instantiate_authentication(); + let authentication = instantiate_authentication_facade(); let expiring_key = authentication .generate_auth_key(Some(Duration::from_secs(100))) @@ -222,13 +224,13 @@ mod tests { use std::time::Duration; use crate::core::authentication::tests::the_tracker_configured_as_private::{ - instantiate_authentication, instantiate_authentication_with_checking_keys_expiration_disabled, + instantiate_authentication_facade, instantiate_authentication_facade_with_checking_keys_expiration_disabled, }; use crate::core::authentication::Key; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication(); + let authentication = instantiate_authentication_facade(); let peer_key = authentication .generate_auth_key(Some(Duration::from_secs(100))) @@ -242,7 +244,7 @@ mod tests { #[tokio::test] async fn it_should_accept_an_expired_key_when_checking_expiration_is_disabled_in_configuration() { - let authentication = instantiate_authentication_with_checking_keys_expiration_disabled(); + let authentication = instantiate_authentication_facade_with_checking_keys_expiration_disabled(); let past_timestamp = Duration::ZERO; @@ -258,13 +260,13 @@ mod tests { mod pre_generated_keys { use crate::core::authentication::tests::the_tracker_configured_as_private::{ - instantiate_authentication, instantiate_authentication_with_checking_keys_expiration_disabled, + instantiate_authentication_facade, instantiate_authentication_facade_with_checking_keys_expiration_disabled, }; use crate::core::authentication::{AddKeyRequest, Key}; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication(); + let authentication = instantiate_authentication_facade(); let peer_key = authentication .add_peer_key(AddKeyRequest { @@ -281,7 +283,7 @@ mod tests { #[tokio::test] async fn it_should_accept_an_expired_key_when_checking_expiration_is_disabled_in_configuration() { - let authentication = instantiate_authentication_with_checking_keys_expiration_disabled(); + let authentication = instantiate_authentication_facade_with_checking_keys_expiration_disabled(); let peer_key = authentication .add_peer_key(AddKeyRequest { @@ -299,11 +301,11 @@ mod tests { mod with_permanent_and { mod randomly_generated_keys { - use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication; + use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication_facade; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication(); + let authentication = instantiate_authentication_facade(); let peer_key = authentication.generate_permanent_auth_key().await.unwrap(); @@ -314,12 +316,12 @@ mod tests { } mod pre_generated_keys { - use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication; + use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication_facade; use crate::core::authentication::{AddKeyRequest, Key}; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication(); + let authentication = instantiate_authentication_facade(); let peer_key = authentication .add_peer_key(AddKeyRequest { From 504357c2d2e1c2db0dcf0f4e2b3673907a87122a Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 08:44:17 +0000 Subject: [PATCH 12/18] refactor: [#1195] inject dependencies in authenticatio::Facade Facade service will be removed. --- src/app_test.rs | 10 ++++++++- src/bootstrap/app.rs | 10 ++++++++- src/bootstrap/jobs/http_tracker.rs | 10 ++++++++- src/bootstrap/jobs/tracker_apis.rs | 10 ++++++++- src/core/authentication/mod.rs | 34 +++++++++++++++++++----------- src/servers/apis/server.rs | 10 ++++++++- src/servers/http/server.rs | 10 ++++++++- src/servers/udp/server/mod.rs | 20 ++++++++++++++++-- 8 files changed, 94 insertions(+), 20 deletions(-) diff --git a/src/app_test.rs b/src/app_test.rs index 884aed6ef..13b10fefa 100644 --- a/src/app_test.rs +++ b/src/app_test.rs @@ -3,6 +3,8 @@ use std::sync::Arc; use torrust_tracker_configuration::Configuration; +use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; +use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::databases::Database; use crate::core::services::initialize_database; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; @@ -25,7 +27,13 @@ pub fn initialize_tracker_dependencies( &config.core, &in_memory_whitelist.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&config.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &config.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); (database, in_memory_whitelist, whitelist_authorization, authentication) } diff --git a/src/bootstrap/app.rs b/src/bootstrap/app.rs index bc6b7a6bd..a87e4ca8e 100644 --- a/src/bootstrap/app.rs +++ b/src/bootstrap/app.rs @@ -22,6 +22,8 @@ use tracing::instrument; use super::config::initialize_configuration; use crate::bootstrap; use crate::container::AppContainer; +use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; +use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -89,7 +91,13 @@ pub fn initialize_app_container(configuration: &Configuration) -> AppContainer { &in_memory_whitelist.clone(), )); let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); - let authentication = Arc::new(authentication::Facade::new(&configuration.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &configuration.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); let tracker = Arc::new(initialize_tracker( configuration, diff --git a/src/bootstrap/jobs/http_tracker.rs b/src/bootstrap/jobs/http_tracker.rs index b07ff935c..abcc2a08c 100644 --- a/src/bootstrap/jobs/http_tracker.rs +++ b/src/bootstrap/jobs/http_tracker.rs @@ -100,6 +100,8 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::http_tracker::start_job; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::services::{initialize_database, initialize_tracker, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -123,7 +125,13 @@ mod tests { &cfg.core, &in_memory_whitelist.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&cfg.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &cfg.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/bootstrap/jobs/tracker_apis.rs b/src/bootstrap/jobs/tracker_apis.rs index 70e2e6737..56e4a2e44 100644 --- a/src/bootstrap/jobs/tracker_apis.rs +++ b/src/bootstrap/jobs/tracker_apis.rs @@ -149,6 +149,8 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::tracker_apis::start_job; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -176,7 +178,13 @@ mod tests { &in_memory_whitelist.clone(), )); let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); - let authentication = Arc::new(authentication::Facade::new(&cfg.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &cfg.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index bab0de8a3..d26379b09 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -7,7 +7,7 @@ use key::repository::persisted::DatabaseKeyRepository; use torrust_tracker_configuration::Core; use torrust_tracker_primitives::DurationSinceUnixEpoch; -use super::databases::{self, Database}; +use super::databases::{self}; use super::error::PeerKeyError; use crate::CurrentClock; @@ -29,12 +29,13 @@ pub struct Facade { impl Facade { #[must_use] - pub fn new(config: &Core, database: &Arc>) -> Self { - let db_key_repository = Arc::new(DatabaseKeyRepository::new(database)); - let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - + pub fn new( + config: &Core, + db_key_repository: &Arc, + in_memory_key_repository: &Arc, + ) -> Self { Self { - authentication_service: service::Service::new(config, &in_memory_key_repository), + authentication_service: service::Service::new(config, in_memory_key_repository), keys_handler: KeysHandler::new(&db_key_repository.clone(), &in_memory_key_repository.clone()), } } @@ -145,20 +146,22 @@ mod tests { mod the_tracker_configured_as_private { + use std::sync::Arc; use std::time::Duration; use torrust_tracker_configuration::v2_0_0::core::PrivateMode; + use torrust_tracker_configuration::Configuration; use torrust_tracker_test_helpers::configuration; use crate::core::authentication; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::services::initialize_database; fn instantiate_authentication_facade() -> authentication::Facade { let config = configuration::ephemeral_private(); - let database = initialize_database(&config); - - authentication::Facade::new(&config.core, &database.clone()) + instantiate_authentication_facade_with_configuration(&config) } fn instantiate_authentication_facade_with_checking_keys_expiration_disabled() -> authentication::Facade { @@ -168,9 +171,16 @@ mod tests { check_keys_expiration: false, }); - let database = initialize_database(&config); - - authentication::Facade::new(&config.core, &database.clone()) + instantiate_authentication_facade_with_configuration(&config) + } + + fn instantiate_authentication_facade_with_configuration(config: &Configuration) -> authentication::Facade { + let database = initialize_database(config); + + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + + authentication::Facade::new(&config.core, &db_key_repository.clone(), &in_memory_key_repository.clone()) } #[tokio::test] diff --git a/src/servers/apis/server.rs b/src/servers/apis/server.rs index a11442a53..b6ff50995 100644 --- a/src/servers/apis/server.rs +++ b/src/servers/apis/server.rs @@ -342,6 +342,8 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::make_rust_tls; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -369,7 +371,13 @@ mod tests { &in_memory_whitelist.clone(), )); let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); - let authentication = Arc::new(authentication::Facade::new(&cfg.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &cfg.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/servers/http/server.rs b/src/servers/http/server.rs index e6370c775..140ef4e07 100644 --- a/src/servers/http/server.rs +++ b/src/servers/http/server.rs @@ -246,6 +246,8 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::make_rust_tls; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -268,7 +270,13 @@ mod tests { &in_memory_whitelist.clone(), )); let _whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); - let authentication = Arc::new(authentication::Facade::new(&cfg.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &cfg.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/servers/udp/server/mod.rs b/src/servers/udp/server/mod.rs index 078510bcd..fafb82997 100644 --- a/src/servers/udp/server/mod.rs +++ b/src/servers/udp/server/mod.rs @@ -64,6 +64,8 @@ mod tests { use super::spawner::Spawner; use super::Server; use crate::bootstrap::app::initialize_global_services; + use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; + use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -88,7 +90,14 @@ mod tests { &in_memory_whitelist.clone(), )); let _whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); - let authentication = Arc::new(authentication::Facade::new(&cfg.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &cfg.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); let udp_trackers = cfg.udp_trackers.clone().expect("missing UDP trackers configuration"); @@ -133,7 +142,14 @@ mod tests { &cfg.core, &in_memory_whitelist.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&cfg.core, &database.clone())); + let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); + let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); + let authentication = Arc::new(authentication::Facade::new( + &cfg.core, + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); let config = &cfg.udp_trackers.as_ref().unwrap().first().unwrap(); From 965e911cdf9a16b57ba0370b358398e2d6a6cc4d Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 09:56:40 +0000 Subject: [PATCH 13/18] refactor: [#1195] inject dependencies into authenticattion::Facade The Facade will be replaced by its dependencies. --- src/app_test.rs | 7 +++++-- src/bootstrap/app.rs | 7 +++++-- src/bootstrap/jobs/http_tracker.rs | 7 +++++-- src/bootstrap/jobs/tracker_apis.rs | 7 +++++-- src/core/authentication/mod.rs | 30 +++++++++++++++--------------- src/servers/apis/server.rs | 7 +++++-- src/servers/http/server.rs | 7 +++++-- src/servers/udp/server/mod.rs | 12 ++++++++---- 8 files changed, 53 insertions(+), 31 deletions(-) diff --git a/src/app_test.rs b/src/app_test.rs index 13b10fefa..6aa318e97 100644 --- a/src/app_test.rs +++ b/src/app_test.rs @@ -3,8 +3,10 @@ use std::sync::Arc; use torrust_tracker_configuration::Configuration; +use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; +use crate::core::authentication::service; use crate::core::databases::Database; use crate::core::services::initialize_database; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; @@ -29,11 +31,12 @@ pub fn initialize_tracker_dependencies( )); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &config.core, + let authentication_service = Arc::new(service::Service::new(&config.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); (database, in_memory_whitelist, whitelist_authorization, authentication) } diff --git a/src/bootstrap/app.rs b/src/bootstrap/app.rs index a87e4ca8e..59b484cce 100644 --- a/src/bootstrap/app.rs +++ b/src/bootstrap/app.rs @@ -22,8 +22,10 @@ use tracing::instrument; use super::config::initialize_configuration; use crate::bootstrap; use crate::container::AppContainer; +use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; +use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -93,11 +95,12 @@ pub fn initialize_app_container(configuration: &Configuration) -> AppContainer { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &configuration.core, + let authentication_service = Arc::new(service::Service::new(&configuration.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); let tracker = Arc::new(initialize_tracker( configuration, diff --git a/src/bootstrap/jobs/http_tracker.rs b/src/bootstrap/jobs/http_tracker.rs index abcc2a08c..a68686224 100644 --- a/src/bootstrap/jobs/http_tracker.rs +++ b/src/bootstrap/jobs/http_tracker.rs @@ -100,8 +100,10 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::http_tracker::start_job; + use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -127,11 +129,12 @@ mod tests { )); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &cfg.core, + let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/bootstrap/jobs/tracker_apis.rs b/src/bootstrap/jobs/tracker_apis.rs index 56e4a2e44..9ddd095c8 100644 --- a/src/bootstrap/jobs/tracker_apis.rs +++ b/src/bootstrap/jobs/tracker_apis.rs @@ -149,8 +149,10 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::tracker_apis::start_job; + use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -180,11 +182,12 @@ mod tests { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &cfg.core, + let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index d26379b09..9ac3638fc 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -1,10 +1,7 @@ use std::sync::Arc; use std::time::Duration; -use handler::{AddKeyRequest, KeysHandler}; -use key::repository::in_memory::InMemoryKeyRepository; -use key::repository::persisted::DatabaseKeyRepository; -use torrust_tracker_configuration::Core; +use handler::AddKeyRequest; use torrust_tracker_primitives::DurationSinceUnixEpoch; use super::databases::{self}; @@ -21,22 +18,18 @@ pub type Error = key::Error; pub struct Facade { /// The authentication service. - authentication_service: service::Service, + authentication_service: Arc, /// The keys handler. - keys_handler: handler::KeysHandler, + keys_handler: Arc, } impl Facade { #[must_use] - pub fn new( - config: &Core, - db_key_repository: &Arc, - in_memory_key_repository: &Arc, - ) -> Self { + pub fn new(authentication_service: &Arc, keys_handler: &Arc) -> Self { Self { - authentication_service: service::Service::new(config, in_memory_key_repository), - keys_handler: KeysHandler::new(&db_key_repository.clone(), &in_memory_key_repository.clone()), + authentication_service: authentication_service.clone(), + keys_handler: keys_handler.clone(), } } @@ -153,9 +146,10 @@ mod tests { use torrust_tracker_configuration::Configuration; use torrust_tracker_test_helpers::configuration; - use crate::core::authentication; + use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::{self, service}; use crate::core::services::initialize_database; fn instantiate_authentication_facade() -> authentication::Facade { @@ -180,7 +174,13 @@ mod tests { let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - authentication::Facade::new(&config.core, &db_key_repository.clone(), &in_memory_key_repository.clone()) + let authentication_service = Arc::new(service::Service::new(&config.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( + &db_key_repository.clone(), + &in_memory_key_repository.clone(), + )); + + authentication::Facade::new(&authentication_service, &keys_handler) } #[tokio::test] diff --git a/src/servers/apis/server.rs b/src/servers/apis/server.rs index b6ff50995..956d54799 100644 --- a/src/servers/apis/server.rs +++ b/src/servers/apis/server.rs @@ -342,8 +342,10 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::make_rust_tls; + use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -373,11 +375,12 @@ mod tests { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &cfg.core, + let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/servers/http/server.rs b/src/servers/http/server.rs index 140ef4e07..751ac5d5c 100644 --- a/src/servers/http/server.rs +++ b/src/servers/http/server.rs @@ -246,8 +246,10 @@ mod tests { use crate::bootstrap::app::initialize_global_services; use crate::bootstrap::jobs::make_rust_tls; + use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -272,11 +274,12 @@ mod tests { let _whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &cfg.core, + let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/servers/udp/server/mod.rs b/src/servers/udp/server/mod.rs index fafb82997..cebeb9b0a 100644 --- a/src/servers/udp/server/mod.rs +++ b/src/servers/udp/server/mod.rs @@ -64,8 +64,10 @@ mod tests { use super::spawner::Spawner; use super::Server; use crate::bootstrap::app::initialize_global_services; + use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; use crate::core::{authentication, whitelist}; @@ -92,11 +94,12 @@ mod tests { let _whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &cfg.core, + let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); @@ -144,11 +147,12 @@ mod tests { )); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication = Arc::new(authentication::Facade::new( - &cfg.core, + let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); + let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); From 457d01b36b6bda0e8e8099a861a79bfaa883a2c1 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 09:59:57 +0000 Subject: [PATCH 14/18] refactor: [#1195] rename service to AuthenticationService --- src/app_test.rs | 2 +- src/bootstrap/app.rs | 5 ++++- src/bootstrap/jobs/http_tracker.rs | 2 +- src/bootstrap/jobs/tracker_apis.rs | 2 +- src/core/authentication/mod.rs | 6 +++--- src/core/authentication/service.rs | 10 +++++----- src/servers/apis/server.rs | 2 +- src/servers/http/server.rs | 2 +- src/servers/udp/server/mod.rs | 4 ++-- 9 files changed, 19 insertions(+), 16 deletions(-) diff --git a/src/app_test.rs b/src/app_test.rs index 6aa318e97..461a18758 100644 --- a/src/app_test.rs +++ b/src/app_test.rs @@ -31,7 +31,7 @@ pub fn initialize_tracker_dependencies( )); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&config.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&config.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), diff --git a/src/bootstrap/app.rs b/src/bootstrap/app.rs index 59b484cce..5c2d47c40 100644 --- a/src/bootstrap/app.rs +++ b/src/bootstrap/app.rs @@ -95,7 +95,10 @@ pub fn initialize_app_container(configuration: &Configuration) -> AppContainer { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&configuration.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new( + &configuration.core, + &in_memory_key_repository, + )); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), diff --git a/src/bootstrap/jobs/http_tracker.rs b/src/bootstrap/jobs/http_tracker.rs index a68686224..a26906fa5 100644 --- a/src/bootstrap/jobs/http_tracker.rs +++ b/src/bootstrap/jobs/http_tracker.rs @@ -129,7 +129,7 @@ mod tests { )); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), diff --git a/src/bootstrap/jobs/tracker_apis.rs b/src/bootstrap/jobs/tracker_apis.rs index 9ddd095c8..dfc5b108a 100644 --- a/src/bootstrap/jobs/tracker_apis.rs +++ b/src/bootstrap/jobs/tracker_apis.rs @@ -182,7 +182,7 @@ mod tests { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index 9ac3638fc..ebc7b1fe1 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -18,7 +18,7 @@ pub type Error = key::Error; pub struct Facade { /// The authentication service. - authentication_service: Arc, + authentication_service: Arc, /// The keys handler. keys_handler: Arc, @@ -26,7 +26,7 @@ pub struct Facade { impl Facade { #[must_use] - pub fn new(authentication_service: &Arc, keys_handler: &Arc) -> Self { + pub fn new(authentication_service: &Arc, keys_handler: &Arc) -> Self { Self { authentication_service: authentication_service.clone(), keys_handler: keys_handler.clone(), @@ -174,7 +174,7 @@ mod tests { let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&config.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&config.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), diff --git a/src/core/authentication/service.rs b/src/core/authentication/service.rs index d7572136f..d100e3a70 100644 --- a/src/core/authentication/service.rs +++ b/src/core/authentication/service.rs @@ -7,7 +7,7 @@ use super::key::repository::in_memory::InMemoryKeyRepository; use super::{key, Error, Key}; #[derive(Debug)] -pub struct Service { +pub struct AuthenticationService { /// The tracker configuration. config: Core, @@ -15,7 +15,7 @@ pub struct Service { in_memory_key_repository: Arc, } -impl Service { +impl AuthenticationService { #[must_use] pub fn new(config: &Core, in_memory_key_repository: &Arc) -> Self { Self { @@ -81,14 +81,14 @@ mod tests { use crate::core::authentication; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; - use crate::core::authentication::service::Service; + use crate::core::authentication::service::AuthenticationService; - fn instantiate_authentication() -> Service { + fn instantiate_authentication() -> AuthenticationService { let config = configuration::ephemeral_private(); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - Service::new(&config.core, &in_memory_key_repository.clone()) + AuthenticationService::new(&config.core, &in_memory_key_repository.clone()) } #[tokio::test] diff --git a/src/servers/apis/server.rs b/src/servers/apis/server.rs index 956d54799..de7845eba 100644 --- a/src/servers/apis/server.rs +++ b/src/servers/apis/server.rs @@ -375,7 +375,7 @@ mod tests { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), diff --git a/src/servers/http/server.rs b/src/servers/http/server.rs index 751ac5d5c..ef13a3535 100644 --- a/src/servers/http/server.rs +++ b/src/servers/http/server.rs @@ -274,7 +274,7 @@ mod tests { let _whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), diff --git a/src/servers/udp/server/mod.rs b/src/servers/udp/server/mod.rs index cebeb9b0a..9658b1bca 100644 --- a/src/servers/udp/server/mod.rs +++ b/src/servers/udp/server/mod.rs @@ -94,7 +94,7 @@ mod tests { let _whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), @@ -147,7 +147,7 @@ mod tests { )); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::Service::new(&cfg.core, &in_memory_key_repository)); + let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), From 747b6089b92aad1c08804d64eec5f35a7ac8e376 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 10:37:57 +0000 Subject: [PATCH 15/18] refactor: [#1195] use AuthenticationService directy Instead of via the authentication::Facade. The Facade will be removed. --- src/app.rs | 1 + src/app_test.rs | 13 ++- src/bootstrap/app.rs | 1 + src/bootstrap/jobs/http_tracker.rs | 15 +++- src/container.rs | 2 + src/core/mod.rs | 6 +- src/core/services/statistics/mod.rs | 3 +- src/core/services/torrent.rs | 14 +-- src/servers/http/server.rs | 38 ++++++++- src/servers/http/v1/handlers/announce.rs | 52 +++++++++--- src/servers/http/v1/handlers/scrape.rs | 85 ++++++++++++++----- src/servers/http/v1/routes.rs | 24 +++++- src/servers/http/v1/services/announce.rs | 4 +- src/servers/http/v1/services/scrape.rs | 6 +- src/servers/udp/handlers.rs | 8 +- tests/servers/api/environment.rs | 5 ++ .../api/v1/contract/context/auth_key.rs | 9 +- tests/servers/http/environment.rs | 6 ++ 18 files changed, 227 insertions(+), 65 deletions(-) diff --git a/src/app.rs b/src/app.rs index da8795ffe..8fa14da54 100644 --- a/src/app.rs +++ b/src/app.rs @@ -100,6 +100,7 @@ pub async fn start(config: &Configuration, app_container: &AppContainer) -> Vec< if let Some(job) = http_tracker::start_job( http_tracker_config, app_container.tracker.clone(), + app_container.authentication_service.clone(), app_container.whitelist_authorization.clone(), app_container.stats_event_sender.clone(), registar.give_form(), diff --git a/src/app_test.rs b/src/app_test.rs index 461a18758..d4e8df961 100644 --- a/src/app_test.rs +++ b/src/app_test.rs @@ -6,7 +6,7 @@ use torrust_tracker_configuration::Configuration; use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; -use crate::core::authentication::service; +use crate::core::authentication::service::{self, AuthenticationService}; use crate::core::databases::Database; use crate::core::services::initialize_database; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; @@ -22,6 +22,7 @@ pub fn initialize_tracker_dependencies( Arc, Arc, Arc, + Arc, ) { let database = initialize_database(config); let in_memory_whitelist = Arc::new(InMemoryWhitelist::default()); @@ -36,7 +37,13 @@ pub fn initialize_tracker_dependencies( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication_facade = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); - (database, in_memory_whitelist, whitelist_authorization, authentication) + ( + database, + in_memory_whitelist, + whitelist_authorization, + authentication_facade, + authentication_service, + ) } diff --git a/src/bootstrap/app.rs b/src/bootstrap/app.rs index 5c2d47c40..31689005d 100644 --- a/src/bootstrap/app.rs +++ b/src/bootstrap/app.rs @@ -114,6 +114,7 @@ pub fn initialize_app_container(configuration: &Configuration) -> AppContainer { AppContainer { tracker, + authentication_service, whitelist_authorization, ban_service, stats_event_sender, diff --git a/src/bootstrap/jobs/http_tracker.rs b/src/bootstrap/jobs/http_tracker.rs index a26906fa5..46e627b6b 100644 --- a/src/bootstrap/jobs/http_tracker.rs +++ b/src/bootstrap/jobs/http_tracker.rs @@ -19,6 +19,7 @@ use torrust_tracker_configuration::HttpTracker; use tracing::instrument; use super::make_rust_tls; +use crate::core::authentication::service::AuthenticationService; use crate::core::statistics::event::sender::Sender; use crate::core::{self, statistics, whitelist}; use crate::servers::http::server::{HttpServer, Launcher}; @@ -34,10 +35,11 @@ use crate::servers::registar::ServiceRegistrationForm; /// /// It would panic if the `config::HttpTracker` struct would contain inappropriate values. /// -#[instrument(skip(config, tracker, whitelist_authorization, stats_event_sender, form))] +#[instrument(skip(config, tracker, authentication_service, whitelist_authorization, stats_event_sender, form))] pub async fn start_job( config: &HttpTracker, tracker: Arc, + authentication_service: Arc, whitelist_authorization: Arc, stats_event_sender: Arc>>, form: ServiceRegistrationForm, @@ -55,6 +57,7 @@ pub async fn start_job( socket, tls, tracker.clone(), + authentication_service.clone(), whitelist_authorization.clone(), stats_event_sender.clone(), form, @@ -70,12 +73,19 @@ async fn start_v1( socket: SocketAddr, tls: Option, tracker: Arc, + authentication_service: Arc, whitelist_authorization: Arc, stats_event_sender: Arc>>, form: ServiceRegistrationForm, ) -> JoinHandle<()> { let server = HttpServer::new(Launcher::new(socket, tls)) - .start(tracker, whitelist_authorization, stats_event_sender, form) + .start( + tracker, + authentication_service, + whitelist_authorization, + stats_event_sender, + form, + ) .await .expect("it should be able to start to the http tracker"); @@ -143,6 +153,7 @@ mod tests { start_job( config, tracker, + authentication_service, whitelist_authorization, stats_event_sender, Registar::default().give_form(), diff --git a/src/container.rs b/src/container.rs index 3c9229b89..0ea8e3c03 100644 --- a/src/container.rs +++ b/src/container.rs @@ -2,6 +2,7 @@ use std::sync::Arc; use tokio::sync::RwLock; +use crate::core::authentication::service::AuthenticationService; use crate::core::statistics::event::sender::Sender; use crate::core::statistics::repository::Repository; use crate::core::whitelist::manager::WhiteListManager; @@ -10,6 +11,7 @@ use crate::servers::udp::server::banning::BanService; pub struct AppContainer { pub tracker: Arc, + pub authentication_service: Arc, pub whitelist_authorization: Arc, pub ban_service: Arc>, pub stats_event_sender: Arc>>, diff --git a/src/core/mod.rs b/src/core/mod.rs index 9a5692690..2b13bc0c0 100644 --- a/src/core/mod.rs +++ b/src/core/mod.rs @@ -816,7 +816,7 @@ mod tests { fn public_tracker() -> Tracker { let config = configuration::ephemeral_public(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); initialize_tracker(&config, &database, &whitelist_authorization, &authentication) @@ -825,7 +825,7 @@ mod tests { fn whitelisted_tracker() -> (Tracker, Arc, Arc) { let config = configuration::ephemeral_listed(); - let (database, in_memory_whitelist, whitelist_authorization, authentication) = + let (database, in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); @@ -839,7 +839,7 @@ mod tests { let mut config = configuration::ephemeral_listed(); config.core.tracker_policy.persistent_torrent_completed_stat = true; - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); initialize_tracker(&config, &database, &whitelist_authorization, &authentication) diff --git a/src/core/services/statistics/mod.rs b/src/core/services/statistics/mod.rs index 4081fd6bb..a30588472 100644 --- a/src/core/services/statistics/mod.rs +++ b/src/core/services/statistics/mod.rs @@ -132,7 +132,8 @@ mod tests { async fn the_statistics_service_should_return_the_tracker_metrics() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + initialize_tracker_dependencies(&config); let (_stats_event_sender, stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_repository = Arc::new(stats_repository); diff --git a/src/core/services/torrent.rs b/src/core/services/torrent.rs index c23c7e04b..462f10101 100644 --- a/src/core/services/torrent.rs +++ b/src/core/services/torrent.rs @@ -142,7 +142,7 @@ mod tests { async fn should_return_none_if_the_tracker_does_not_have_the_torrent() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let tracker = initialize_tracker(&config, &database, &whitelist_authorization, &authentication); @@ -162,7 +162,7 @@ mod tests { async fn should_return_the_torrent_info_if_the_tracker_has_the_torrent() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let tracker = Arc::new(initialize_tracker( @@ -213,7 +213,7 @@ mod tests { async fn should_return_an_empty_result_if_the_tracker_does_not_have_any_torrent() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let tracker = Arc::new(initialize_tracker( @@ -232,7 +232,7 @@ mod tests { async fn should_return_a_summarized_info_for_all_torrents() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let tracker = Arc::new(initialize_tracker( @@ -264,7 +264,7 @@ mod tests { async fn should_allow_limiting_the_number_of_torrents_in_the_result() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let tracker = Arc::new(initialize_tracker( @@ -294,7 +294,7 @@ mod tests { async fn should_allow_using_pagination_in_the_result() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let tracker = Arc::new(initialize_tracker( @@ -333,7 +333,7 @@ mod tests { async fn should_return_torrents_ordered_by_info_hash() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let tracker = Arc::new(initialize_tracker( diff --git a/src/servers/http/server.rs b/src/servers/http/server.rs index ef13a3535..3bc6773dd 100644 --- a/src/servers/http/server.rs +++ b/src/servers/http/server.rs @@ -11,6 +11,7 @@ use tracing::instrument; use super::v1::routes::router; use crate::bootstrap::jobs::Started; +use crate::core::authentication::service::AuthenticationService; use crate::core::{statistics, whitelist, Tracker}; use crate::servers::custom_axum_server::{self, TimeoutAcceptor}; use crate::servers::http::HTTP_TRACKER_LOG_TARGET; @@ -42,10 +43,19 @@ pub struct Launcher { } impl Launcher { - #[instrument(skip(self, tracker, whitelist_authorization, stats_event_sender, tx_start, rx_halt))] + #[instrument(skip( + self, + tracker, + authentication_service, + whitelist_authorization, + stats_event_sender, + tx_start, + rx_halt + ))] fn start( &self, tracker: Arc, + authentication_service: Arc, whitelist_authorization: Arc, stats_event_sender: Arc>>, tx_start: Sender, @@ -67,7 +77,13 @@ impl Launcher { tracing::info!(target: HTTP_TRACKER_LOG_TARGET, "Starting on: {protocol}://{}", address); - let app = router(tracker, whitelist_authorization, stats_event_sender, address); + let app = router( + tracker, + authentication_service, + whitelist_authorization, + stats_event_sender, + address, + ); let running = Box::pin(async { match tls { @@ -163,6 +179,7 @@ impl HttpServer { pub async fn start( self, tracker: Arc, + authentication_service: Arc, whitelist_authorization: Arc, stats_event_sender: Arc>>, form: ServiceRegistrationForm, @@ -173,7 +190,14 @@ impl HttpServer { let launcher = self.state.launcher; let task = tokio::spawn(async move { - let server = launcher.start(tracker, whitelist_authorization, stats_event_sender, tx_start, rx_halt); + let server = launcher.start( + tracker, + authentication_service, + whitelist_authorization, + stats_event_sender, + tx_start, + rx_halt, + ); server.await; @@ -296,7 +320,13 @@ mod tests { let stopped = HttpServer::new(Launcher::new(bind_to, tls)); let started = stopped - .start(tracker, whitelist_authorization, stats_event_sender, register.give_form()) + .start( + tracker, + authentication_service, + whitelist_authorization, + stats_event_sender, + register.give_form(), + ) .await .expect("it should start the server"); let stopped = started.stop().await.expect("it should stop the server"); diff --git a/src/servers/http/v1/handlers/announce.rs b/src/servers/http/v1/handlers/announce.rs index 7af2b9261..fbadde967 100644 --- a/src/servers/http/v1/handlers/announce.rs +++ b/src/servers/http/v1/handlers/announce.rs @@ -21,6 +21,7 @@ use torrust_tracker_clock::clock::Time; use torrust_tracker_primitives::core::AnnounceData; use torrust_tracker_primitives::peer; +use crate::core::authentication::service::AuthenticationService; use crate::core::authentication::Key; use crate::core::statistics::event::sender::Sender; use crate::core::{whitelist, PeersWanted, Tracker}; @@ -38,6 +39,7 @@ use crate::CurrentClock; pub async fn handle_without_key( State(state): State<( Arc, + Arc, Arc, Arc>>, )>, @@ -46,7 +48,16 @@ pub async fn handle_without_key( ) -> Response { tracing::debug!("http announce request: {:#?}", announce_request); - handle(&state.0, &state.1, &state.2, &announce_request, &client_ip_sources, None).await + handle( + &state.0, + &state.1, + &state.2, + &state.3, + &announce_request, + &client_ip_sources, + None, + ) + .await } /// It handles the `announce` request when the HTTP tracker requires @@ -56,6 +67,7 @@ pub async fn handle_without_key( pub async fn handle_with_key( State(state): State<( Arc, + Arc, Arc, Arc>>, )>, @@ -65,7 +77,16 @@ pub async fn handle_with_key( ) -> Response { tracing::debug!("http announce request: {:#?}", announce_request); - handle(&state.0, &state.1, &state.2, &announce_request, &client_ip_sources, Some(key)).await + handle( + &state.0, + &state.1, + &state.2, + &state.3, + &announce_request, + &client_ip_sources, + Some(key), + ) + .await } /// It handles the `announce` request. @@ -74,6 +95,7 @@ pub async fn handle_with_key( /// `unauthenticated` modes. async fn handle( tracker: &Arc, + authentication_service: &Arc, whitelist_authorization: &Arc, opt_stats_event_sender: &Arc>>, announce_request: &Announce, @@ -82,6 +104,7 @@ async fn handle( ) -> Response { let announce_data = match handle_announce( tracker, + authentication_service, whitelist_authorization, opt_stats_event_sender, announce_request, @@ -104,6 +127,7 @@ async fn handle( async fn handle_announce( tracker: &Arc, + authentication_service: &Arc, whitelist_authorization: &Arc, opt_stats_event_sender: &Arc>>, announce_request: &Announce, @@ -113,7 +137,7 @@ async fn handle_announce( // Authentication if tracker.requires_authentication() { match maybe_key { - Some(key) => match tracker.authentication.authenticate(&key).await { + Some(key) => match authentication_service.authenticate(&key).await { Ok(()) => (), Err(error) => return Err(responses::error::Error::from(error)), }, @@ -220,6 +244,7 @@ mod tests { use torrust_tracker_test_helpers::configuration; use crate::app_test::initialize_tracker_dependencies; + use crate::core::authentication::service::AuthenticationService; use crate::core::services::{initialize_tracker, statistics}; use crate::core::statistics::event::sender::Sender; use crate::core::{whitelist, Tracker}; @@ -228,6 +253,7 @@ mod tests { Arc, Arc>>, Arc, + Arc, ); fn private_tracker() -> TrackerAndDeps { @@ -248,7 +274,8 @@ mod tests { /// Initialize tracker's dependencies and tracker. fn initialize_tracker_and_deps(config: &Configuration) -> TrackerAndDeps { - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + initialize_tracker_dependencies(config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_event_sender = Arc::new(stats_event_sender); @@ -259,7 +286,7 @@ mod tests { &authentication, )); - (tracker, stats_event_sender, whitelist_authorization) + (tracker, stats_event_sender, whitelist_authorization, authentication_service) } fn sample_announce_request() -> Announce { @@ -302,7 +329,7 @@ mod tests { #[tokio::test] async fn it_should_fail_when_the_authentication_key_is_missing() { - let (tracker, stats_event_sender, whitelist_authorization) = private_tracker(); + let (tracker, stats_event_sender, whitelist_authorization, authentication_service) = private_tracker(); let tracker = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -311,6 +338,7 @@ mod tests { let response = handle_announce( &tracker, + &authentication_service, &whitelist_authorization, &stats_event_sender, &sample_announce_request(), @@ -328,7 +356,7 @@ mod tests { #[tokio::test] async fn it_should_fail_when_the_authentication_key_is_invalid() { - let (tracker, stats_event_sender, whitelist_authorization) = private_tracker(); + let (tracker, stats_event_sender, whitelist_authorization, authentication_service) = private_tracker(); let tracker = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -339,6 +367,7 @@ mod tests { let response = handle_announce( &tracker, + &authentication_service, &whitelist_authorization, &stats_event_sender, &sample_announce_request(), @@ -362,7 +391,7 @@ mod tests { #[tokio::test] async fn it_should_fail_when_the_announced_torrent_is_not_whitelisted() { - let (tracker, stats_event_sender, whitelist_authorization) = whitelisted_tracker(); + let (tracker, stats_event_sender, whitelist_authorization, authentication_service) = whitelisted_tracker(); let tracker = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -371,6 +400,7 @@ mod tests { let response = handle_announce( &tracker, + &authentication_service, &whitelist_authorization, &stats_event_sender, &announce_request, @@ -402,7 +432,7 @@ mod tests { #[tokio::test] async fn it_should_fail_when_the_right_most_x_forwarded_for_header_ip_is_not_available() { - let (tracker, stats_event_sender, whitelist_authorization) = tracker_on_reverse_proxy(); + let (tracker, stats_event_sender, whitelist_authorization, authentication_service) = tracker_on_reverse_proxy(); let tracker = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -414,6 +444,7 @@ mod tests { let response = handle_announce( &tracker, + &authentication_service, &whitelist_authorization, &stats_event_sender, &sample_announce_request(), @@ -442,7 +473,7 @@ mod tests { #[tokio::test] async fn it_should_fail_when_the_client_ip_from_the_connection_info_is_not_available() { - let (tracker, stats_event_sender, whitelist_authorization) = tracker_not_on_reverse_proxy(); + let (tracker, stats_event_sender, whitelist_authorization, authentication_service) = tracker_not_on_reverse_proxy(); let tracker = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -454,6 +485,7 @@ mod tests { let response = handle_announce( &tracker, + &authentication_service, &whitelist_authorization, &stats_event_sender, &sample_announce_request(), diff --git a/src/servers/http/v1/handlers/scrape.rs b/src/servers/http/v1/handlers/scrape.rs index 062a017f8..f7be42bff 100644 --- a/src/servers/http/v1/handlers/scrape.rs +++ b/src/servers/http/v1/handlers/scrape.rs @@ -15,6 +15,7 @@ use bittorrent_http_protocol::v1::services::peer_ip_resolver::{self, ClientIpSou use hyper::StatusCode; use torrust_tracker_primitives::core::ScrapeData; +use crate::core::authentication::service::AuthenticationService; use crate::core::authentication::Key; use crate::core::statistics::event::sender::Sender; use crate::core::Tracker; @@ -28,13 +29,13 @@ use crate::servers::http::v1::services; #[allow(clippy::unused_async)] #[allow(clippy::type_complexity)] pub async fn handle_without_key( - State(state): State<(Arc, Arc>>)>, + State(state): State<(Arc, Arc, Arc>>)>, ExtractRequest(scrape_request): ExtractRequest, ExtractClientIpSources(client_ip_sources): ExtractClientIpSources, ) -> Response { tracing::debug!("http scrape request: {:#?}", &scrape_request); - handle(&state.0, &state.1, &scrape_request, &client_ip_sources, None).await + handle(&state.0, &state.1, &state.2, &scrape_request, &client_ip_sources, None).await } /// It handles the `scrape` request when the HTTP tracker is configured @@ -44,24 +45,34 @@ pub async fn handle_without_key( #[allow(clippy::unused_async)] #[allow(clippy::type_complexity)] pub async fn handle_with_key( - State(state): State<(Arc, Arc>>)>, + State(state): State<(Arc, Arc, Arc>>)>, ExtractRequest(scrape_request): ExtractRequest, ExtractClientIpSources(client_ip_sources): ExtractClientIpSources, ExtractKey(key): ExtractKey, ) -> Response { tracing::debug!("http scrape request: {:#?}", &scrape_request); - handle(&state.0, &state.1, &scrape_request, &client_ip_sources, Some(key)).await + handle(&state.0, &state.1, &state.2, &scrape_request, &client_ip_sources, Some(key)).await } async fn handle( tracker: &Arc, + authentication_service: &Arc, stats_event_sender: &Arc>>, scrape_request: &Scrape, client_ip_sources: &ClientIpSources, maybe_key: Option, ) -> Response { - let scrape_data = match handle_scrape(tracker, stats_event_sender, scrape_request, client_ip_sources, maybe_key).await { + let scrape_data = match handle_scrape( + tracker, + authentication_service, + stats_event_sender, + scrape_request, + client_ip_sources, + maybe_key, + ) + .await + { Ok(scrape_data) => scrape_data, Err(error) => return (StatusCode::OK, error.write()).into_response(), }; @@ -76,6 +87,7 @@ async fn handle( async fn handle_scrape( tracker: &Arc, + authentication_service: &Arc, opt_stats_event_sender: &Arc>>, scrape_request: &Scrape, client_ip_sources: &ClientIpSources, @@ -84,7 +96,7 @@ async fn handle_scrape( // Authentication let return_real_scrape_data = if tracker.requires_authentication() { match maybe_key { - Some(key) => match tracker.authentication.authenticate(&key).await { + Some(key) => match authentication_service.authenticate(&key).await { Ok(()) => true, Err(_error) => false, }, @@ -119,6 +131,7 @@ fn build_response(scrape_data: ScrapeData) -> Response { mod tests { use std::net::IpAddr; use std::str::FromStr; + use std::sync::Arc; use bittorrent_http_protocol::v1::requests::scrape::Scrape; use bittorrent_http_protocol::v1::responses; @@ -127,54 +140,83 @@ mod tests { use torrust_tracker_test_helpers::configuration; use crate::app_test::initialize_tracker_dependencies; + use crate::core::authentication::service::AuthenticationService; use crate::core::services::{initialize_tracker, statistics}; use crate::core::Tracker; - fn private_tracker() -> (Tracker, Option>) { + fn private_tracker() -> ( + Tracker, + Option>, + Arc, + ) { let config = configuration::ephemeral_private(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + initialize_tracker_dependencies(&config); + let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( initialize_tracker(&config, &database, &whitelist_authorization, &authentication), stats_event_sender, + authentication_service, ) } - fn whitelisted_tracker() -> (Tracker, Option>) { + fn whitelisted_tracker() -> ( + Tracker, + Option>, + Arc, + ) { let config = configuration::ephemeral_listed(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + initialize_tracker_dependencies(&config); + let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( initialize_tracker(&config, &database, &whitelist_authorization, &authentication), stats_event_sender, + authentication_service, ) } - fn tracker_on_reverse_proxy() -> (Tracker, Option>) { + fn tracker_on_reverse_proxy() -> ( + Tracker, + Option>, + Arc, + ) { let config = configuration::ephemeral_with_reverse_proxy(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + initialize_tracker_dependencies(&config); + let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( initialize_tracker(&config, &database, &whitelist_authorization, &authentication), stats_event_sender, + authentication_service, ) } - fn tracker_not_on_reverse_proxy() -> (Tracker, Option>) { + fn tracker_not_on_reverse_proxy() -> ( + Tracker, + Option>, + Arc, + ) { let config = configuration::ephemeral_without_reverse_proxy(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + initialize_tracker_dependencies(&config); + let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( initialize_tracker(&config, &database, &whitelist_authorization, &authentication), stats_event_sender, + authentication_service, ) } @@ -210,7 +252,7 @@ mod tests { #[tokio::test] async fn it_should_return_zeroed_swarm_metadata_when_the_authentication_key_is_missing() { - let (tracker, stats_event_sender) = private_tracker(); + let (tracker, stats_event_sender, authentication_service) = private_tracker(); let tracker = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -219,6 +261,7 @@ mod tests { let scrape_data = handle_scrape( &tracker, + &authentication_service, &stats_event_sender, &scrape_request, &sample_client_ip_sources(), @@ -234,7 +277,7 @@ mod tests { #[tokio::test] async fn it_should_return_zeroed_swarm_metadata_when_the_authentication_key_is_invalid() { - let (tracker, stats_event_sender) = private_tracker(); + let (tracker, stats_event_sender, authentication_service) = private_tracker(); let tracker = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -244,6 +287,7 @@ mod tests { let scrape_data = handle_scrape( &tracker, + &authentication_service, &stats_event_sender, &scrape_request, &sample_client_ip_sources(), @@ -269,7 +313,7 @@ mod tests { #[tokio::test] async fn it_should_return_zeroed_swarm_metadata_when_the_torrent_is_not_whitelisted() { - let (tracker, stats_event_sender) = whitelisted_tracker(); + let (tracker, stats_event_sender, authentication_service) = whitelisted_tracker(); let tracker: Arc = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -277,6 +321,7 @@ mod tests { let scrape_data = handle_scrape( &tracker, + &authentication_service, &stats_event_sender, &scrape_request, &sample_client_ip_sources(), @@ -302,7 +347,7 @@ mod tests { #[tokio::test] async fn it_should_fail_when_the_right_most_x_forwarded_for_header_ip_is_not_available() { - let (tracker, stats_event_sender) = tracker_on_reverse_proxy(); + let (tracker, stats_event_sender, authentication_service) = tracker_on_reverse_proxy(); let tracker: Arc = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -313,6 +358,7 @@ mod tests { let response = handle_scrape( &tracker, + &authentication_service, &stats_event_sender, &sample_scrape_request(), &client_ip_sources, @@ -339,7 +385,7 @@ mod tests { #[tokio::test] async fn it_should_fail_when_the_client_ip_from_the_connection_info_is_not_available() { - let (tracker, stats_event_sender) = tracker_not_on_reverse_proxy(); + let (tracker, stats_event_sender, authentication_service) = tracker_not_on_reverse_proxy(); let tracker: Arc = Arc::new(tracker); let stats_event_sender = Arc::new(stats_event_sender); @@ -350,6 +396,7 @@ mod tests { let response = handle_scrape( &tracker, + &authentication_service, &stats_event_sender, &sample_scrape_request(), &client_ip_sources, diff --git a/src/servers/http/v1/routes.rs b/src/servers/http/v1/routes.rs index d37c55c7a..7a1465500 100644 --- a/src/servers/http/v1/routes.rs +++ b/src/servers/http/v1/routes.rs @@ -22,6 +22,7 @@ use tower_http::LatencyUnit; use tracing::{instrument, Level, Span}; use super::handlers::{announce, health_check, scrape}; +use crate::core::authentication::service::AuthenticationService; use crate::core::statistics::event::sender::Sender; use crate::core::{whitelist, Tracker}; use crate::servers::http::HTTP_TRACKER_LOG_TARGET; @@ -32,9 +33,16 @@ use crate::servers::logging::Latency; /// > **NOTICE**: it's added a layer to get the client IP from the connection /// > info. The tracker could use the connection info to get the client IP. #[allow(clippy::needless_pass_by_value)] -#[instrument(skip(tracker, whitelist_authorization, stats_event_sender, server_socket_addr))] +#[instrument(skip( + tracker, + authentication_service, + whitelist_authorization, + stats_event_sender, + server_socket_addr +))] pub fn router( tracker: Arc, + authentication_service: Arc, whitelist_authorization: Arc, stats_event_sender: Arc>>, server_socket_addr: SocketAddr, @@ -47,6 +55,7 @@ pub fn router( "/announce", get(announce::handle_without_key).with_state(( tracker.clone(), + authentication_service.clone(), whitelist_authorization.clone(), stats_event_sender.clone(), )), @@ -55,6 +64,7 @@ pub fn router( "/announce/{key}", get(announce::handle_with_key).with_state(( tracker.clone(), + authentication_service.clone(), whitelist_authorization.clone(), stats_event_sender.clone(), )), @@ -62,11 +72,19 @@ pub fn router( // Scrape request .route( "/scrape", - get(scrape::handle_without_key).with_state((tracker.clone(), stats_event_sender.clone())), + get(scrape::handle_without_key).with_state(( + tracker.clone(), + authentication_service.clone(), + stats_event_sender.clone(), + )), ) .route( "/scrape/{key}", - get(scrape::handle_with_key).with_state((tracker.clone(), stats_event_sender.clone())), + get(scrape::handle_with_key).with_state(( + tracker.clone(), + authentication_service.clone(), + stats_event_sender.clone(), + )), ) // Add extension to get the client IP from the connection info .layer(SecureClientIpSource::ConnectInfo.into_extension()) diff --git a/src/servers/http/v1/services/announce.rs b/src/servers/http/v1/services/announce.rs index 929b00ff4..446af1db3 100644 --- a/src/servers/http/v1/services/announce.rs +++ b/src/servers/http/v1/services/announce.rs @@ -73,7 +73,7 @@ mod tests { fn public_tracker() -> (Tracker, Arc>>) { let config = configuration::ephemeral_public(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_event_sender = Arc::new(stats_event_sender); @@ -131,7 +131,7 @@ mod tests { fn test_tracker_factory() -> Tracker { let config = configuration::ephemeral(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); Tracker::new(&config.core, &database, &whitelist_authorization, &authentication).unwrap() diff --git a/src/servers/http/v1/services/scrape.rs b/src/servers/http/v1/services/scrape.rs index 856b2ae72..35b264363 100644 --- a/src/servers/http/v1/services/scrape.rs +++ b/src/servers/http/v1/services/scrape.rs @@ -87,7 +87,8 @@ mod tests { fn public_tracker() -> Tracker { let config = configuration::ephemeral_public(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + initialize_tracker_dependencies(&config); initialize_tracker(&config, &database, &whitelist_authorization, &authentication) } @@ -115,7 +116,8 @@ mod tests { fn test_tracker_factory() -> Tracker { let config = configuration::ephemeral(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + initialize_tracker_dependencies(&config); Tracker::new(&config.core, &database, &whitelist_authorization, &authentication).unwrap() } diff --git a/src/servers/udp/handlers.rs b/src/servers/udp/handlers.rs index 67bb35c5a..f0f7719e2 100644 --- a/src/servers/udp/handlers.rs +++ b/src/servers/udp/handlers.rs @@ -516,7 +516,8 @@ mod tests { } fn initialize_tracker_and_deps(config: &Configuration) -> TrackerAndDeps { - let (database, in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(config); + let (database, in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + initialize_tracker_dependencies(config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_event_sender = Arc::new(stats_event_sender); let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); @@ -634,7 +635,8 @@ mod tests { fn test_tracker_factory() -> (Arc, Arc) { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + initialize_tracker_dependencies(&config); let tracker = Arc::new(Tracker::new(&config.core, &database, &whitelist_authorization, &authentication).unwrap()); @@ -1381,7 +1383,7 @@ mod tests { async fn the_peer_ip_should_be_changed_to_the_external_ip_in_the_tracker_configuration() { let config = Arc::new(TrackerConfigurationBuilder::default().with_external_ip("::126.0.0.1").into()); - let (database, _in_memory_whitelist, whitelist_authorization, authentication) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); let mut stats_event_sender_mock = statistics::event::sender::MockSender::new(); diff --git a/tests/servers/api/environment.rs b/tests/servers/api/environment.rs index 3bac7e570..3e8fedd0e 100644 --- a/tests/servers/api/environment.rs +++ b/tests/servers/api/environment.rs @@ -8,6 +8,7 @@ use torrust_tracker_api_client::connection_info::{ConnectionInfo, Origin}; use torrust_tracker_configuration::{Configuration, HttpApi}; use torrust_tracker_lib::bootstrap::app::{initialize_app_container, initialize_global_services}; use torrust_tracker_lib::bootstrap::jobs::make_rust_tls; +use torrust_tracker_lib::core::authentication::service::AuthenticationService; use torrust_tracker_lib::core::statistics::event::sender::Sender; use torrust_tracker_lib::core::statistics::repository::Repository; use torrust_tracker_lib::core::whitelist::manager::WhiteListManager; @@ -23,6 +24,7 @@ where { pub config: Arc, pub tracker: Arc, + pub authentication_service: Arc, pub stats_event_sender: Arc>>, pub stats_repository: Arc, pub whitelist_manager: Arc, @@ -58,6 +60,7 @@ impl Environment { Self { config, tracker: app_container.tracker.clone(), + authentication_service: app_container.authentication_service.clone(), stats_event_sender: app_container.stats_event_sender.clone(), stats_repository: app_container.stats_repository.clone(), whitelist_manager: app_container.whitelist_manager.clone(), @@ -73,6 +76,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker.clone(), + authentication_service: self.authentication_service.clone(), stats_event_sender: self.stats_event_sender.clone(), stats_repository: self.stats_repository.clone(), whitelist_manager: self.whitelist_manager.clone(), @@ -104,6 +108,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker, + authentication_service: self.authentication_service, stats_event_sender: self.stats_event_sender, stats_repository: self.stats_repository, whitelist_manager: self.whitelist_manager, diff --git a/tests/servers/api/v1/contract/context/auth_key.rs b/tests/servers/api/v1/contract/context/auth_key.rs index cee6b4034..6a270f894 100644 --- a/tests/servers/api/v1/contract/context/auth_key.rs +++ b/tests/servers/api/v1/contract/context/auth_key.rs @@ -36,8 +36,7 @@ async fn should_allow_generating_a_new_random_auth_key() { let auth_key_resource = assert_auth_key_utf8(response).await; assert!(env - .tracker - .authentication + .authentication_service .authenticate(&auth_key_resource.key.parse::().unwrap()) .await .is_ok()); @@ -66,8 +65,7 @@ async fn should_allow_uploading_a_preexisting_auth_key() { let auth_key_resource = assert_auth_key_utf8(response).await; assert!(env - .tracker - .authentication + .authentication_service .authenticate(&auth_key_resource.key.parse::().unwrap()) .await .is_ok()); @@ -499,8 +497,7 @@ mod deprecated_generate_key_endpoint { let auth_key_resource = assert_auth_key_utf8(response).await; assert!(env - .tracker - .authentication + .authentication_service .authenticate(&auth_key_resource.key.parse::().unwrap()) .await .is_ok()); diff --git a/tests/servers/http/environment.rs b/tests/servers/http/environment.rs index a8e5fc572..85921cd37 100644 --- a/tests/servers/http/environment.rs +++ b/tests/servers/http/environment.rs @@ -5,6 +5,7 @@ use futures::executor::block_on; use torrust_tracker_configuration::{Configuration, HttpTracker}; use torrust_tracker_lib::bootstrap::app::{initialize_app_container, initialize_global_services}; use torrust_tracker_lib::bootstrap::jobs::make_rust_tls; +use torrust_tracker_lib::core::authentication::service::AuthenticationService; use torrust_tracker_lib::core::statistics::event::sender::Sender; use torrust_tracker_lib::core::statistics::repository::Repository; use torrust_tracker_lib::core::whitelist::manager::WhiteListManager; @@ -16,6 +17,7 @@ use torrust_tracker_primitives::peer; pub struct Environment { pub config: Arc, pub tracker: Arc, + pub authentication_service: Arc, pub stats_event_sender: Arc>>, pub stats_repository: Arc, pub whitelist_authorization: Arc, @@ -54,6 +56,7 @@ impl Environment { Self { config, tracker: app_container.tracker.clone(), + authentication_service: app_container.authentication_service.clone(), stats_event_sender: app_container.stats_event_sender.clone(), stats_repository: app_container.stats_repository.clone(), whitelist_authorization: app_container.whitelist_authorization.clone(), @@ -68,6 +71,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker.clone(), + authentication_service: self.authentication_service.clone(), whitelist_authorization: self.whitelist_authorization.clone(), stats_event_sender: self.stats_event_sender.clone(), stats_repository: self.stats_repository.clone(), @@ -77,6 +81,7 @@ impl Environment { .server .start( self.tracker, + self.authentication_service, self.whitelist_authorization, self.stats_event_sender, self.registar.give_form(), @@ -96,6 +101,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker, + authentication_service: self.authentication_service, whitelist_authorization: self.whitelist_authorization, stats_event_sender: self.stats_event_sender, stats_repository: self.stats_repository, From 661fe6abe741321ecdc3cb8e3519bd5bb5a2b714 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 10:49:59 +0000 Subject: [PATCH 16/18] refactor: [#1195] remove AuthenticationService from authentication Facade It's now used directly. --- src/app_test.rs | 2 +- src/bootstrap/app.rs | 2 +- src/bootstrap/jobs/http_tracker.rs | 2 +- src/bootstrap/jobs/tracker_apis.rs | 4 +- src/core/authentication/mod.rs | 117 ++++++++++++----------------- src/servers/apis/server.rs | 4 +- src/servers/http/server.rs | 2 +- src/servers/udp/server/mod.rs | 8 +- 8 files changed, 60 insertions(+), 81 deletions(-) diff --git a/src/app_test.rs b/src/app_test.rs index d4e8df961..a8ad9f967 100644 --- a/src/app_test.rs +++ b/src/app_test.rs @@ -37,7 +37,7 @@ pub fn initialize_tracker_dependencies( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication_facade = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication_facade = Arc::new(authentication::Facade::new(&keys_handler)); ( database, diff --git a/src/bootstrap/app.rs b/src/bootstrap/app.rs index 31689005d..b5067f5f6 100644 --- a/src/bootstrap/app.rs +++ b/src/bootstrap/app.rs @@ -103,7 +103,7 @@ pub fn initialize_app_container(configuration: &Configuration) -> AppContainer { &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication = Arc::new(authentication::Facade::new(&keys_handler)); let tracker = Arc::new(initialize_tracker( configuration, diff --git a/src/bootstrap/jobs/http_tracker.rs b/src/bootstrap/jobs/http_tracker.rs index 46e627b6b..a0e11a688 100644 --- a/src/bootstrap/jobs/http_tracker.rs +++ b/src/bootstrap/jobs/http_tracker.rs @@ -144,7 +144,7 @@ mod tests { &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication = Arc::new(authentication::Facade::new(&keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/bootstrap/jobs/tracker_apis.rs b/src/bootstrap/jobs/tracker_apis.rs index dfc5b108a..39bfc112d 100644 --- a/src/bootstrap/jobs/tracker_apis.rs +++ b/src/bootstrap/jobs/tracker_apis.rs @@ -182,12 +182,12 @@ mod tests { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); + let _authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication = Arc::new(authentication::Facade::new(&keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index ebc7b1fe1..ac5db55d1 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -17,32 +17,18 @@ pub type Key = key::Key; pub type Error = key::Error; pub struct Facade { - /// The authentication service. - authentication_service: Arc, - /// The keys handler. keys_handler: Arc, } impl Facade { #[must_use] - pub fn new(authentication_service: &Arc, keys_handler: &Arc) -> Self { + pub fn new(keys_handler: &Arc) -> Self { Self { - authentication_service: authentication_service.clone(), keys_handler: keys_handler.clone(), } } - /// It authenticates the peer `key` against the `Tracker` authentication - /// key list. - /// - /// # Errors - /// - /// Will return an error if the the authentication key cannot be verified. - pub async fn authenticate(&self, key: &Key) -> Result<(), Error> { - self.authentication_service.authenticate(key).await - } - /// Adds new peer keys to the tracker. /// /// Keys can be pre-generated or randomly created. They can also be permanent or expire. @@ -149,26 +135,30 @@ mod tests { use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::service::AuthenticationService; use crate::core::authentication::{self, service}; use crate::core::services::initialize_database; - fn instantiate_authentication_facade() -> authentication::Facade { + fn instantiate_keys_manager_and_authentication() -> (authentication::Facade, Arc) { let config = configuration::ephemeral_private(); - instantiate_authentication_facade_with_configuration(&config) + instantiate_keys_manager_and_authentication_with_configuration(&config) } - fn instantiate_authentication_facade_with_checking_keys_expiration_disabled() -> authentication::Facade { + fn instantiate_keys_manager_and_authentication_with_checking_keys_expiration_disabled( + ) -> (authentication::Facade, Arc) { let mut config = configuration::ephemeral_private(); config.core.private_mode = Some(PrivateMode { check_keys_expiration: false, }); - instantiate_authentication_facade_with_configuration(&config) + instantiate_keys_manager_and_authentication_with_configuration(&config) } - fn instantiate_authentication_facade_with_configuration(config: &Configuration) -> authentication::Facade { + fn instantiate_keys_manager_and_authentication_with_configuration( + config: &Configuration, + ) -> (authentication::Facade, Arc) { let database = initialize_database(config); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); @@ -180,52 +170,40 @@ mod tests { &in_memory_key_repository.clone(), )); - authentication::Facade::new(&authentication_service, &keys_handler) + let facade = authentication::Facade::new(&keys_handler); + + (facade, authentication_service) } #[tokio::test] async fn it_should_remove_an_authentication_key() { - let authentication = instantiate_authentication_facade(); + let (keys_manager, authentication_service) = instantiate_keys_manager_and_authentication(); - let expiring_key = authentication - .generate_auth_key(Some(Duration::from_secs(100))) - .await - .unwrap(); + let expiring_key = keys_manager.generate_auth_key(Some(Duration::from_secs(100))).await.unwrap(); - let result = authentication.remove_auth_key(&expiring_key.key()).await; + let result = keys_manager.remove_auth_key(&expiring_key.key()).await; assert!(result.is_ok()); // The key should no longer be valid - assert!(authentication - .authentication_service - .authenticate(&expiring_key.key()) - .await - .is_err()); + assert!(authentication_service.authenticate(&expiring_key.key()).await.is_err()); } #[tokio::test] async fn it_should_load_authentication_keys_from_the_database() { - let authentication = instantiate_authentication_facade(); + let (keys_manager, authentication_service) = instantiate_keys_manager_and_authentication(); - let expiring_key = authentication - .generate_auth_key(Some(Duration::from_secs(100))) - .await - .unwrap(); + let expiring_key = keys_manager.generate_auth_key(Some(Duration::from_secs(100))).await.unwrap(); // Remove the newly generated key in memory - authentication.remove_in_memory_auth_key(&expiring_key.key()).await; + keys_manager.remove_in_memory_auth_key(&expiring_key.key()).await; - let result = authentication.load_keys_from_database().await; + let result = keys_manager.load_keys_from_database().await; assert!(result.is_ok()); // The key should no longer be valid - assert!(authentication - .authentication_service - .authenticate(&expiring_key.key()) - .await - .is_ok()); + assert!(authentication_service.authenticate(&expiring_key.key()).await.is_ok()); } mod with_expiring_and { @@ -234,51 +212,51 @@ mod tests { use std::time::Duration; use crate::core::authentication::tests::the_tracker_configured_as_private::{ - instantiate_authentication_facade, instantiate_authentication_facade_with_checking_keys_expiration_disabled, + instantiate_keys_manager_and_authentication, + instantiate_keys_manager_and_authentication_with_checking_keys_expiration_disabled, }; use crate::core::authentication::Key; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication_facade(); + let (keys_manager, authentication_service) = instantiate_keys_manager_and_authentication(); - let peer_key = authentication - .generate_auth_key(Some(Duration::from_secs(100))) - .await - .unwrap(); + let peer_key = keys_manager.generate_auth_key(Some(Duration::from_secs(100))).await.unwrap(); - let result = authentication.authenticate(&peer_key.key()).await; + let result = authentication_service.authenticate(&peer_key.key()).await; assert!(result.is_ok()); } #[tokio::test] async fn it_should_accept_an_expired_key_when_checking_expiration_is_disabled_in_configuration() { - let authentication = instantiate_authentication_facade_with_checking_keys_expiration_disabled(); + let (keys_manager, authentication_service) = + instantiate_keys_manager_and_authentication_with_checking_keys_expiration_disabled(); let past_timestamp = Duration::ZERO; - let peer_key = authentication + let peer_key = keys_manager .add_auth_key(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap(), Some(past_timestamp)) .await .unwrap(); - assert!(authentication.authenticate(&peer_key.key()).await.is_ok()); + assert!(authentication_service.authenticate(&peer_key.key()).await.is_ok()); } } mod pre_generated_keys { use crate::core::authentication::tests::the_tracker_configured_as_private::{ - instantiate_authentication_facade, instantiate_authentication_facade_with_checking_keys_expiration_disabled, + instantiate_keys_manager_and_authentication, + instantiate_keys_manager_and_authentication_with_checking_keys_expiration_disabled, }; use crate::core::authentication::{AddKeyRequest, Key}; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication_facade(); + let (keys_manager, authentication_service) = instantiate_keys_manager_and_authentication(); - let peer_key = authentication + let peer_key = keys_manager .add_peer_key(AddKeyRequest { opt_key: Some(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap().to_string()), opt_seconds_valid: Some(100), @@ -286,16 +264,17 @@ mod tests { .await .unwrap(); - let result = authentication.authenticate(&peer_key.key()).await; + let result = authentication_service.authenticate(&peer_key.key()).await; assert!(result.is_ok()); } #[tokio::test] async fn it_should_accept_an_expired_key_when_checking_expiration_is_disabled_in_configuration() { - let authentication = instantiate_authentication_facade_with_checking_keys_expiration_disabled(); + let (keys_manager, authentication_service) = + instantiate_keys_manager_and_authentication_with_checking_keys_expiration_disabled(); - let peer_key = authentication + let peer_key = keys_manager .add_peer_key(AddKeyRequest { opt_key: Some(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap().to_string()), opt_seconds_valid: Some(0), @@ -303,7 +282,7 @@ mod tests { .await .unwrap(); - assert!(authentication.authenticate(&peer_key.key()).await.is_ok()); + assert!(authentication_service.authenticate(&peer_key.key()).await.is_ok()); } } } @@ -311,29 +290,29 @@ mod tests { mod with_permanent_and { mod randomly_generated_keys { - use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication_facade; + use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_keys_manager_and_authentication; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication_facade(); + let (keys_manager, authentication_service) = instantiate_keys_manager_and_authentication(); - let peer_key = authentication.generate_permanent_auth_key().await.unwrap(); + let peer_key = keys_manager.generate_permanent_auth_key().await.unwrap(); - let result = authentication.authenticate(&peer_key.key()).await; + let result = authentication_service.authenticate(&peer_key.key()).await; assert!(result.is_ok()); } } mod pre_generated_keys { - use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_authentication_facade; + use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_keys_manager_and_authentication; use crate::core::authentication::{AddKeyRequest, Key}; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { - let authentication = instantiate_authentication_facade(); + let (keys_manager, authentication_service) = instantiate_keys_manager_and_authentication(); - let peer_key = authentication + let peer_key = keys_manager .add_peer_key(AddKeyRequest { opt_key: Some(Key::new("YZSl4lMZupRuOpSRC3krIKR5BPB14nrJ").unwrap().to_string()), opt_seconds_valid: None, @@ -341,7 +320,7 @@ mod tests { .await .unwrap(); - let result = authentication.authenticate(&peer_key.key()).await; + let result = authentication_service.authenticate(&peer_key.key()).await; assert!(result.is_ok()); } diff --git a/src/servers/apis/server.rs b/src/servers/apis/server.rs index de7845eba..c9fc2f185 100644 --- a/src/servers/apis/server.rs +++ b/src/servers/apis/server.rs @@ -375,12 +375,12 @@ mod tests { let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); + let _authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication = Arc::new(authentication::Facade::new(&keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/servers/http/server.rs b/src/servers/http/server.rs index 3bc6773dd..a9b618c84 100644 --- a/src/servers/http/server.rs +++ b/src/servers/http/server.rs @@ -303,7 +303,7 @@ mod tests { &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication = Arc::new(authentication::Facade::new(&keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); diff --git a/src/servers/udp/server/mod.rs b/src/servers/udp/server/mod.rs index 9658b1bca..c507b3cb6 100644 --- a/src/servers/udp/server/mod.rs +++ b/src/servers/udp/server/mod.rs @@ -94,12 +94,12 @@ mod tests { let _whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); + let _authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication = Arc::new(authentication::Facade::new(&keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); @@ -147,12 +147,12 @@ mod tests { )); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); - let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); + let _authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); let keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&authentication_service, &keys_handler)); + let authentication = Arc::new(authentication::Facade::new(&keys_handler)); let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); From 77eccdc33da86f8029b6fee7e467697650fd4fa6 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 10:50:49 +0000 Subject: [PATCH 17/18] fix: [#1195] format --- src/servers/http/v1/services/announce.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/servers/http/v1/services/announce.rs b/src/servers/http/v1/services/announce.rs index 446af1db3..2f2876f5b 100644 --- a/src/servers/http/v1/services/announce.rs +++ b/src/servers/http/v1/services/announce.rs @@ -73,7 +73,8 @@ mod tests { fn public_tracker() -> (Tracker, Arc>>) { let config = configuration::ephemeral_public(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = initialize_tracker_dependencies(&config); + let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + initialize_tracker_dependencies(&config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_event_sender = Arc::new(stats_event_sender); From dff6bca1bbf587074ad31ddd8a73f3c4c15ba058 Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Wed, 22 Jan 2025 11:27:57 +0000 Subject: [PATCH 18/18] refactor: [#1195] remove authentication::Facade service --- src/app.rs | 4 +- src/app_test.rs | 14 +- src/bootstrap/app.rs | 12 +- src/bootstrap/jobs/http_tracker.rs | 7 +- src/bootstrap/jobs/tracker_apis.rs | 23 ++- src/container.rs | 5 +- src/core/authentication/handler.rs | 6 +- src/core/authentication/mod.rs | 132 ++---------------- src/core/mod.rs | 17 +-- src/core/services/mod.rs | 5 +- src/core/services/statistics/mod.rs | 9 +- src/core/services/torrent.rs | 58 ++------ src/servers/apis/routes.rs | 5 + src/servers/apis/server.rs | 14 +- .../apis/v1/context/auth_key/handlers.rs | 27 ++-- .../apis/v1/context/auth_key/routes.rs | 12 +- src/servers/apis/v1/routes.rs | 5 +- src/servers/http/server.rs | 7 +- src/servers/http/v1/handlers/announce.rs | 9 +- src/servers/http/v1/handlers/scrape.rs | 16 +-- src/servers/http/v1/services/announce.rs | 8 +- src/servers/http/v1/services/scrape.rs | 8 +- src/servers/udp/handlers.rs | 18 +-- src/servers/udp/server/mod.rs | 12 +- tests/servers/api/environment.rs | 6 + .../api/v1/contract/context/auth_key.rs | 21 +-- tests/servers/http/environment.rs | 5 + tests/servers/http/v1/contract.rs | 6 +- 28 files changed, 161 insertions(+), 310 deletions(-) diff --git a/src/app.rs b/src/app.rs index 8fa14da54..e41f227e7 100644 --- a/src/app.rs +++ b/src/app.rs @@ -52,8 +52,7 @@ pub async fn start(config: &Configuration, app_container: &AppContainer) -> Vec< // Load peer keys if app_container.tracker.is_private() { app_container - .tracker - .authentication + .keys_handler .load_keys_from_database() .await .expect("Could not retrieve keys from database."); @@ -120,6 +119,7 @@ pub async fn start(config: &Configuration, app_container: &AppContainer) -> Vec< if let Some(job) = tracker_apis::start_job( http_api_config, app_container.tracker.clone(), + app_container.keys_handler.clone(), app_container.whitelist_manager.clone(), app_container.ban_service.clone(), app_container.stats_event_sender.clone(), diff --git a/src/app_test.rs b/src/app_test.rs index a8ad9f967..929a23418 100644 --- a/src/app_test.rs +++ b/src/app_test.rs @@ -9,8 +9,8 @@ use crate::core::authentication::key::repository::persisted::DatabaseKeyReposito use crate::core::authentication::service::{self, AuthenticationService}; use crate::core::databases::Database; use crate::core::services::initialize_database; +use crate::core::whitelist; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; -use crate::core::{authentication, whitelist}; /// Initialize the tracker dependencies. #[allow(clippy::type_complexity)] @@ -21,7 +21,6 @@ pub fn initialize_tracker_dependencies( Arc>, Arc, Arc, - Arc, Arc, ) { let database = initialize_database(config); @@ -33,17 +32,10 @@ pub fn initialize_tracker_dependencies( let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); let authentication_service = Arc::new(service::AuthenticationService::new(&config.core, &in_memory_key_repository)); - let keys_handler = Arc::new(KeysHandler::new( + let _keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication_facade = Arc::new(authentication::Facade::new(&keys_handler)); - ( - database, - in_memory_whitelist, - whitelist_authorization, - authentication_facade, - authentication_service, - ) + (database, in_memory_whitelist, whitelist_authorization, authentication_service) } diff --git a/src/bootstrap/app.rs b/src/bootstrap/app.rs index b5067f5f6..a0c7887cf 100644 --- a/src/bootstrap/app.rs +++ b/src/bootstrap/app.rs @@ -27,8 +27,8 @@ use crate::core::authentication::key::repository::in_memory::InMemoryKeyReposito use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; +use crate::core::whitelist; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; -use crate::core::{authentication, whitelist}; use crate::servers::udp::server::banning::BanService; use crate::servers::udp::server::launcher::MAX_CONNECTION_ID_ERRORS_PER_IP; use crate::shared::crypto::ephemeral_instance_keys; @@ -103,24 +103,18 @@ pub fn initialize_app_container(configuration: &Configuration) -> AppContainer { &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&keys_handler)); - let tracker = Arc::new(initialize_tracker( - configuration, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(configuration, &database, &whitelist_authorization)); AppContainer { tracker, + keys_handler, authentication_service, whitelist_authorization, ban_service, stats_event_sender, stats_repository, whitelist_manager, - authentication, } } diff --git a/src/bootstrap/jobs/http_tracker.rs b/src/bootstrap/jobs/http_tracker.rs index a0e11a688..4df669675 100644 --- a/src/bootstrap/jobs/http_tracker.rs +++ b/src/bootstrap/jobs/http_tracker.rs @@ -115,8 +115,8 @@ mod tests { use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, statistics}; + use crate::core::whitelist; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; - use crate::core::{authentication, whitelist}; use crate::servers::http::Version; use crate::servers::registar::Registar; @@ -140,13 +140,12 @@ mod tests { let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); - let keys_handler = Arc::new(KeysHandler::new( + let _keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&keys_handler)); - let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization)); let version = Version::V1; diff --git a/src/bootstrap/jobs/tracker_apis.rs b/src/bootstrap/jobs/tracker_apis.rs index 39bfc112d..9bb7e6d45 100644 --- a/src/bootstrap/jobs/tracker_apis.rs +++ b/src/bootstrap/jobs/tracker_apis.rs @@ -30,6 +30,7 @@ use torrust_tracker_configuration::{AccessTokens, HttpApi}; use tracing::instrument; use super::make_rust_tls; +use crate::core::authentication::handler::KeysHandler; use crate::core::statistics::event::sender::Sender; use crate::core::statistics::repository::Repository; use crate::core::whitelist::manager::WhiteListManager; @@ -60,10 +61,20 @@ pub struct ApiServerJobStarted(); /// /// #[allow(clippy::too_many_arguments)] -#[instrument(skip(config, tracker, whitelist_manager, ban_service, stats_event_sender, stats_repository, form))] +#[instrument(skip( + config, + tracker, + keys_handler, + whitelist_manager, + ban_service, + stats_event_sender, + stats_repository, + form +))] pub async fn start_job( config: &HttpApi, tracker: Arc, + keys_handler: Arc, whitelist_manager: Arc, ban_service: Arc>, stats_event_sender: Arc>>, @@ -85,6 +96,7 @@ pub async fn start_job( bind_to, tls, tracker.clone(), + keys_handler.clone(), whitelist_manager.clone(), ban_service.clone(), stats_event_sender.clone(), @@ -103,6 +115,7 @@ pub async fn start_job( socket, tls, tracker, + keys_handler, whitelist_manager, ban_service, stats_event_sender, @@ -114,6 +127,7 @@ async fn start_v1( socket: SocketAddr, tls: Option, tracker: Arc, + keys_handler: Arc, whitelist_manager: Arc, ban_service: Arc>, stats_event_sender: Arc>>, @@ -124,6 +138,7 @@ async fn start_v1( let server = ApiServer::new(Launcher::new(socket, tls)) .start( tracker, + keys_handler, whitelist_manager, stats_event_sender, stats_repository, @@ -154,8 +169,8 @@ mod tests { use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; + use crate::core::whitelist; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; - use crate::core::{authentication, whitelist}; use crate::servers::apis::Version; use crate::servers::registar::Registar; use crate::servers::udp::server::banning::BanService; @@ -187,15 +202,15 @@ mod tests { &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&keys_handler)); - let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization)); let version = Version::V1; start_job( config, tracker, + keys_handler, whitelist_manager, ban_service, stats_event_sender, diff --git a/src/container.rs b/src/container.rs index 0ea8e3c03..14c4b5d7b 100644 --- a/src/container.rs +++ b/src/container.rs @@ -2,20 +2,21 @@ use std::sync::Arc; use tokio::sync::RwLock; +use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::service::AuthenticationService; use crate::core::statistics::event::sender::Sender; use crate::core::statistics::repository::Repository; use crate::core::whitelist::manager::WhiteListManager; -use crate::core::{authentication, whitelist, Tracker}; +use crate::core::{whitelist, Tracker}; use crate::servers::udp::server::banning::BanService; pub struct AppContainer { pub tracker: Arc, + pub keys_handler: Arc, pub authentication_service: Arc, pub whitelist_authorization: Arc, pub ban_service: Arc>, pub stats_event_sender: Arc>>, pub stats_repository: Arc, pub whitelist_manager: Arc, - pub authentication: Arc, } diff --git a/src/core/authentication/handler.rs b/src/core/authentication/handler.rs index 3ada2b110..17033aefc 100644 --- a/src/core/authentication/handler.rs +++ b/src/core/authentication/handler.rs @@ -303,7 +303,8 @@ mod tests { use torrust_tracker_clock::clock::Time; use crate::core::authentication::handler::tests::the_keys_handler_when_tracker_is_configured_as_private::instantiate_keys_handler; - use crate::core::authentication::{AddKeyRequest, Key}; + use crate::core::authentication::handler::AddKeyRequest; + use crate::core::authentication::Key; use crate::CurrentClock; #[tokio::test] @@ -344,7 +345,8 @@ mod tests { mod pre_generated_keys { use crate::core::authentication::handler::tests::the_keys_handler_when_tracker_is_configured_as_private::instantiate_keys_handler; - use crate::core::authentication::{AddKeyRequest, Key}; + use crate::core::authentication::handler::AddKeyRequest; + use crate::core::authentication::Key; #[tokio::test] async fn it_should_add_a_pre_generated_key() { diff --git a/src/core/authentication/mod.rs b/src/core/authentication/mod.rs index ac5db55d1..799263752 100644 --- a/src/core/authentication/mod.rs +++ b/src/core/authentication/mod.rs @@ -1,11 +1,3 @@ -use std::sync::Arc; -use std::time::Duration; - -use handler::AddKeyRequest; -use torrust_tracker_primitives::DurationSinceUnixEpoch; - -use super::databases::{self}; -use super::error::PeerKeyError; use crate::CurrentClock; pub mod handler; @@ -16,113 +8,11 @@ pub type PeerKey = key::PeerKey; pub type Key = key::Key; pub type Error = key::Error; -pub struct Facade { - /// The keys handler. - keys_handler: Arc, -} - -impl Facade { - #[must_use] - pub fn new(keys_handler: &Arc) -> Self { - Self { - keys_handler: keys_handler.clone(), - } - } - - /// Adds new peer keys to the tracker. - /// - /// Keys can be pre-generated or randomly created. They can also be permanent or expire. - /// - /// # Errors - /// - /// Will return an error if: - /// - /// - The key duration overflows the duration type maximum value. - /// - The provided pre-generated key is invalid. - /// - The key could not been persisted due to database issues. - pub async fn add_peer_key(&self, add_key_req: AddKeyRequest) -> Result { - self.keys_handler.add_peer_key(add_key_req).await - } - - /// It generates a new permanent authentication key. - /// - /// Authentication keys are used by HTTP trackers. - /// - /// # Errors - /// - /// Will return a `database::Error` if unable to add the `auth_key` to the database. - pub async fn generate_permanent_auth_key(&self) -> Result { - self.keys_handler.generate_permanent_auth_key().await - } - - /// It generates a new expiring authentication key. - /// - /// Authentication keys are used by HTTP trackers. - /// - /// # Errors - /// - /// Will return a `database::Error` if unable to add the `auth_key` to the database. - /// - /// # Arguments - /// - /// * `lifetime` - The duration in seconds for the new key. The key will be - /// no longer valid after `lifetime` seconds. - pub async fn generate_auth_key(&self, lifetime: Option) -> Result { - self.keys_handler.generate_auth_key(lifetime).await - } - - /// It adds a pre-generated authentication key. - /// - /// Authentication keys are used by HTTP trackers. - /// - /// # Errors - /// - /// Will return a `database::Error` if unable to add the `auth_key` to the - /// database. For example, if the key already exist. - /// - /// # Arguments - /// - /// * `key` - The pre-generated key. - /// * `lifetime` - The duration in seconds for the new key. The key will be - /// no longer valid after `lifetime` seconds. - pub async fn add_auth_key( - &self, - key: Key, - valid_until: Option, - ) -> Result { - self.keys_handler.add_auth_key(key, valid_until).await - } - - /// It removes an authentication key. - /// - /// # Errors - /// - /// Will return a `database::Error` if unable to remove the `key` to the database. - pub async fn remove_auth_key(&self, key: &Key) -> Result<(), databases::error::Error> { - self.keys_handler.remove_auth_key(key).await - } - - /// It removes an authentication key from memory. - pub async fn remove_in_memory_auth_key(&self, key: &Key) { - self.keys_handler.remove_in_memory_auth_key(key).await; - } - - /// The `Tracker` stores the authentication keys in memory and in the - /// database. In case you need to restart the `Tracker` you can load the - /// keys from the database into memory with this function. Keys are - /// automatically stored in the database when they are generated. - /// - /// # Errors - /// - /// Will return a `database::Error` if unable to `load_keys` from the database. - pub async fn load_keys_from_database(&self) -> Result<(), databases::error::Error> { - self.keys_handler.load_keys_from_database().await - } -} - #[cfg(test)] mod tests { + // Integration tests for authentication. + mod the_tracker_configured_as_private { use std::sync::Arc; @@ -135,18 +25,18 @@ mod tests { use crate::core::authentication::handler::KeysHandler; use crate::core::authentication::key::repository::in_memory::InMemoryKeyRepository; use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; + use crate::core::authentication::service; use crate::core::authentication::service::AuthenticationService; - use crate::core::authentication::{self, service}; use crate::core::services::initialize_database; - fn instantiate_keys_manager_and_authentication() -> (authentication::Facade, Arc) { + fn instantiate_keys_manager_and_authentication() -> (Arc, Arc) { let config = configuration::ephemeral_private(); instantiate_keys_manager_and_authentication_with_configuration(&config) } fn instantiate_keys_manager_and_authentication_with_checking_keys_expiration_disabled( - ) -> (authentication::Facade, Arc) { + ) -> (Arc, Arc) { let mut config = configuration::ephemeral_private(); config.core.private_mode = Some(PrivateMode { @@ -158,7 +48,7 @@ mod tests { fn instantiate_keys_manager_and_authentication_with_configuration( config: &Configuration, - ) -> (authentication::Facade, Arc) { + ) -> (Arc, Arc) { let database = initialize_database(config); let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); @@ -170,9 +60,7 @@ mod tests { &in_memory_key_repository.clone(), )); - let facade = authentication::Facade::new(&keys_handler); - - (facade, authentication_service) + (keys_handler, authentication_service) } #[tokio::test] @@ -246,11 +134,12 @@ mod tests { mod pre_generated_keys { + use crate::core::authentication::handler::AddKeyRequest; use crate::core::authentication::tests::the_tracker_configured_as_private::{ instantiate_keys_manager_and_authentication, instantiate_keys_manager_and_authentication_with_checking_keys_expiration_disabled, }; - use crate::core::authentication::{AddKeyRequest, Key}; + use crate::core::authentication::Key; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { @@ -305,8 +194,9 @@ mod tests { } mod pre_generated_keys { + use crate::core::authentication::handler::AddKeyRequest; use crate::core::authentication::tests::the_tracker_configured_as_private::instantiate_keys_manager_and_authentication; - use crate::core::authentication::{AddKeyRequest, Key}; + use crate::core::authentication::Key; #[tokio::test] async fn it_should_authenticate_a_peer_with_the_key() { diff --git a/src/core/mod.rs b/src/core/mod.rs index 2b13bc0c0..26ef69bfa 100644 --- a/src/core/mod.rs +++ b/src/core/mod.rs @@ -490,9 +490,6 @@ pub struct Tracker { /// The in-memory torrents repository. torrents: Arc, - - /// The service to authenticate peers. - pub authentication: Arc, } /// How many peers the peer announcing wants in the announce response. @@ -547,14 +544,12 @@ impl Tracker { config: &Core, database: &Arc>, whitelist_authorization: &Arc, - authentication: &Arc, ) -> Result { Ok(Tracker { config: config.clone(), database: database.clone(), whitelist_authorization: whitelist_authorization.clone(), torrents: Arc::default(), - authentication: authentication.clone(), }) } @@ -816,21 +811,21 @@ mod tests { fn public_tracker() -> Tracker { let config = configuration::ephemeral_public(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - initialize_tracker(&config, &database, &whitelist_authorization, &authentication) + initialize_tracker(&config, &database, &whitelist_authorization) } fn whitelisted_tracker() -> (Tracker, Arc, Arc) { let config = configuration::ephemeral_listed(); - let (database, in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); - let tracker = initialize_tracker(&config, &database, &whitelist_authorization, &authentication); + let tracker = initialize_tracker(&config, &database, &whitelist_authorization); (tracker, whitelist_authorization, whitelist_manager) } @@ -839,10 +834,10 @@ mod tests { let mut config = configuration::ephemeral_listed(); config.core.tracker_policy.persistent_torrent_completed_stat = true; - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - initialize_tracker(&config, &database, &whitelist_authorization, &authentication) + initialize_tracker(&config, &database, &whitelist_authorization) } fn sample_info_hash() -> InfoHash { diff --git a/src/core/services/mod.rs b/src/core/services/mod.rs index b1d0d441d..611ea24d2 100644 --- a/src/core/services/mod.rs +++ b/src/core/services/mod.rs @@ -14,10 +14,10 @@ use torrust_tracker_configuration::v2_0_0::database; use torrust_tracker_configuration::Configuration; use super::databases::{self, Database}; +use super::whitelist; use super::whitelist::manager::WhiteListManager; use super::whitelist::repository::in_memory::InMemoryWhitelist; use super::whitelist::repository::persisted::DatabaseWhitelist; -use super::{authentication, whitelist}; use crate::core::Tracker; /// It returns a new tracker building its dependencies. @@ -30,9 +30,8 @@ pub fn initialize_tracker( config: &Configuration, database: &Arc>, whitelist_authorization: &Arc, - authentication: &Arc, ) -> Tracker { - match Tracker::new(&Arc::new(config).core, database, whitelist_authorization, authentication) { + match Tracker::new(&Arc::new(config).core, database, whitelist_authorization) { Ok(tracker) => tracker, Err(error) => { panic!("{}", error) diff --git a/src/core/services/statistics/mod.rs b/src/core/services/statistics/mod.rs index a30588472..cc59bcf12 100644 --- a/src/core/services/statistics/mod.rs +++ b/src/core/services/statistics/mod.rs @@ -132,17 +132,12 @@ mod tests { async fn the_statistics_service_should_return_the_tracker_metrics() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); let (_stats_event_sender, stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_repository = Arc::new(stats_repository); - let tracker = Arc::new(initialize_tracker( - &config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(&config, &database, &whitelist_authorization)); let ban_service = Arc::new(RwLock::new(BanService::new(MAX_CONNECTION_ID_ERRORS_PER_IP))); diff --git a/src/core/services/torrent.rs b/src/core/services/torrent.rs index 462f10101..9b7254098 100644 --- a/src/core/services/torrent.rs +++ b/src/core/services/torrent.rs @@ -142,10 +142,10 @@ mod tests { async fn should_return_none_if_the_tracker_does_not_have_the_torrent() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = initialize_tracker(&config, &database, &whitelist_authorization, &authentication); + let tracker = initialize_tracker(&config, &database, &whitelist_authorization); let tracker = Arc::new(tracker); @@ -162,15 +162,10 @@ mod tests { async fn should_return_the_torrent_info_if_the_tracker_has_the_torrent() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = Arc::new(initialize_tracker( - &config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(&config, &database, &whitelist_authorization)); let hash = "9e0217d0fa71c87332cd8bf9dbeabcb2c2cf3c4d".to_owned(); let info_hash = InfoHash::from_str(&hash).unwrap(); @@ -213,15 +208,10 @@ mod tests { async fn should_return_an_empty_result_if_the_tracker_does_not_have_any_torrent() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = Arc::new(initialize_tracker( - &config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(&config, &database, &whitelist_authorization)); let torrents = get_torrents_page(tracker.clone(), Some(&Pagination::default())).await; @@ -232,15 +222,10 @@ mod tests { async fn should_return_a_summarized_info_for_all_torrents() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = Arc::new(initialize_tracker( - &config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(&config, &database, &whitelist_authorization)); let hash = "9e0217d0fa71c87332cd8bf9dbeabcb2c2cf3c4d".to_owned(); let info_hash = InfoHash::from_str(&hash).unwrap(); @@ -264,15 +249,10 @@ mod tests { async fn should_allow_limiting_the_number_of_torrents_in_the_result() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = Arc::new(initialize_tracker( - &config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(&config, &database, &whitelist_authorization)); let hash1 = "9e0217d0fa71c87332cd8bf9dbeabcb2c2cf3c4d".to_owned(); let info_hash1 = InfoHash::from_str(&hash1).unwrap(); @@ -294,15 +274,10 @@ mod tests { async fn should_allow_using_pagination_in_the_result() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = Arc::new(initialize_tracker( - &config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(&config, &database, &whitelist_authorization)); let hash1 = "9e0217d0fa71c87332cd8bf9dbeabcb2c2cf3c4d".to_owned(); let info_hash1 = InfoHash::from_str(&hash1).unwrap(); @@ -333,15 +308,10 @@ mod tests { async fn should_return_torrents_ordered_by_info_hash() { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = Arc::new(initialize_tracker( - &config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(&config, &database, &whitelist_authorization)); let hash1 = "9e0217d0fa71c87332cd8bf9dbeabcb2c2cf3c4d".to_owned(); let info_hash1 = InfoHash::from_str(&hash1).unwrap(); diff --git a/src/servers/apis/routes.rs b/src/servers/apis/routes.rs index a5c33d5ee..4a005393d 100644 --- a/src/servers/apis/routes.rs +++ b/src/servers/apis/routes.rs @@ -30,6 +30,7 @@ use tracing::{instrument, Level, Span}; use super::v1; use super::v1::context::health_check::handlers::health_check_handler; use super::v1::middlewares::auth::State; +use crate::core::authentication::handler::KeysHandler; use crate::core::statistics::event::sender::Sender; use crate::core::statistics::repository::Repository; use crate::core::whitelist::manager::WhiteListManager; @@ -39,9 +40,11 @@ use crate::servers::logging::Latency; use crate::servers::udp::server::banning::BanService; /// Add all API routes to the router. +#[allow(clippy::too_many_arguments)] #[allow(clippy::needless_pass_by_value)] #[instrument(skip( tracker, + keys_handler, whitelist_manager, ban_service, stats_event_sender, @@ -50,6 +53,7 @@ use crate::servers::udp::server::banning::BanService; ))] pub fn router( tracker: Arc, + keys_handler: Arc, whitelist_manager: Arc, ban_service: Arc>, stats_event_sender: Arc>>, @@ -65,6 +69,7 @@ pub fn router( api_url_prefix, router, tracker.clone(), + &keys_handler.clone(), &whitelist_manager.clone(), ban_service.clone(), stats_event_sender.clone(), diff --git a/src/servers/apis/server.rs b/src/servers/apis/server.rs index c9fc2f185..f219ca023 100644 --- a/src/servers/apis/server.rs +++ b/src/servers/apis/server.rs @@ -39,6 +39,7 @@ use tracing::{instrument, Level}; use super::routes::router; use crate::bootstrap::jobs::Started; +use crate::core::authentication::handler::KeysHandler; use crate::core::statistics::repository::Repository; use crate::core::whitelist::manager::WhiteListManager; use crate::core::{statistics, Tracker}; @@ -127,10 +128,11 @@ impl ApiServer { /// /// It would panic if the bound socket address cannot be sent back to this starter. #[allow(clippy::too_many_arguments)] - #[instrument(skip(self, tracker, whitelist_manager, stats_event_sender, ban_service, stats_repository, form, access_tokens), err, ret(Display, level = Level::INFO))] + #[instrument(skip(self, tracker, keys_handler, whitelist_manager, stats_event_sender, ban_service, stats_repository, form, access_tokens), err, ret(Display, level = Level::INFO))] pub async fn start( self, tracker: Arc, + keys_handler: Arc, whitelist_manager: Arc, stats_event_sender: Arc>>, stats_repository: Arc, @@ -149,6 +151,7 @@ impl ApiServer { let _task = launcher .start( tracker, + keys_handler, whitelist_manager, ban_service, stats_event_sender, @@ -259,6 +262,7 @@ impl Launcher { #[instrument(skip( self, tracker, + keys_handler, whitelist_manager, ban_service, stats_event_sender, @@ -270,6 +274,7 @@ impl Launcher { pub fn start( &self, tracker: Arc, + keys_handler: Arc, whitelist_manager: Arc, ban_service: Arc>, stats_event_sender: Arc>>, @@ -283,6 +288,7 @@ impl Launcher { let router = router( tracker, + keys_handler, whitelist_manager, ban_service, stats_event_sender, @@ -347,8 +353,8 @@ mod tests { use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; + use crate::core::whitelist; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; - use crate::core::{authentication, whitelist}; use crate::servers::apis::server::{ApiServer, Launcher}; use crate::servers::registar::Registar; use crate::servers::udp::server::banning::BanService; @@ -380,9 +386,8 @@ mod tests { &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&keys_handler)); - let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization)); let bind_to = config.bind_address; @@ -399,6 +404,7 @@ mod tests { let started = stopped .start( tracker, + keys_handler, whitelist_manager, stats_event_sender, stats_repository, diff --git a/src/servers/apis/v1/context/auth_key/handlers.rs b/src/servers/apis/v1/context/auth_key/handlers.rs index f0c131bbf..045a9d211 100644 --- a/src/servers/apis/v1/context/auth_key/handlers.rs +++ b/src/servers/apis/v1/context/auth_key/handlers.rs @@ -12,9 +12,8 @@ use super::responses::{ auth_key_response, failed_to_delete_key_response, failed_to_generate_key_response, failed_to_reload_keys_response, invalid_auth_key_duration_response, invalid_auth_key_response, }; -use crate::core::authentication::handler::AddKeyRequest; +use crate::core::authentication::handler::{AddKeyRequest, KeysHandler}; use crate::core::authentication::Key; -use crate::core::Tracker; use crate::servers::apis::v1::context::auth_key::resources::AuthKey; use crate::servers::apis::v1::responses::{invalid_auth_key_param_response, ok_response}; @@ -32,11 +31,10 @@ use crate::servers::apis::v1::responses::{invalid_auth_key_param_response, ok_re /// Refer to the [API endpoint documentation](crate::servers::apis::v1::context::auth_key#generate-a-new-authentication-key) /// for more information about this endpoint. pub async fn add_auth_key_handler( - State(tracker): State>, + State(keys_handler): State>, extract::Json(add_key_form): extract::Json, ) -> Response { - match tracker - .authentication + match keys_handler .add_peer_key(AddKeyRequest { opt_key: add_key_form.opt_key.clone(), opt_seconds_valid: add_key_form.opt_seconds_valid, @@ -67,13 +65,12 @@ pub async fn add_auth_key_handler( /// for more information about this endpoint. /// /// This endpoint has been deprecated. Use [`add_auth_key_handler`]. -pub async fn generate_auth_key_handler(State(tracker): State>, Path(seconds_valid_or_key): Path) -> Response { +pub async fn generate_auth_key_handler( + State(keys_handler): State>, + Path(seconds_valid_or_key): Path, +) -> Response { let seconds_valid = seconds_valid_or_key; - match tracker - .authentication - .generate_auth_key(Some(Duration::from_secs(seconds_valid))) - .await - { + match keys_handler.generate_auth_key(Some(Duration::from_secs(seconds_valid))).await { Ok(auth_key) => auth_key_response(&AuthKey::from(auth_key)), Err(e) => failed_to_generate_key_response(e), } @@ -109,12 +106,12 @@ pub struct KeyParam(String); /// Refer to the [API endpoint documentation](crate::servers::apis::v1::context::auth_key#delete-an-authentication-key) /// for more information about this endpoint. pub async fn delete_auth_key_handler( - State(tracker): State>, + State(keys_handler): State>, Path(seconds_valid_or_key): Path, ) -> Response { match Key::from_str(&seconds_valid_or_key.0) { Err(_) => invalid_auth_key_param_response(&seconds_valid_or_key.0), - Ok(key) => match tracker.authentication.remove_auth_key(&key).await { + Ok(key) => match keys_handler.remove_auth_key(&key).await { Ok(()) => ok_response(), Err(e) => failed_to_delete_key_response(e), }, @@ -133,8 +130,8 @@ pub async fn delete_auth_key_handler( /// /// Refer to the [API endpoint documentation](crate::servers::apis::v1::context::auth_key#reload-authentication-keys) /// for more information about this endpoint. -pub async fn reload_keys_handler(State(tracker): State>) -> Response { - match tracker.authentication.load_keys_from_database().await { +pub async fn reload_keys_handler(State(keys_handler): State>) -> Response { + match keys_handler.load_keys_from_database().await { Ok(()) => ok_response(), Err(e) => failed_to_reload_keys_response(e), } diff --git a/src/servers/apis/v1/context/auth_key/routes.rs b/src/servers/apis/v1/context/auth_key/routes.rs index ac11281ee..45aeb02ec 100644 --- a/src/servers/apis/v1/context/auth_key/routes.rs +++ b/src/servers/apis/v1/context/auth_key/routes.rs @@ -12,10 +12,10 @@ use axum::routing::{get, post}; use axum::Router; use super::handlers::{add_auth_key_handler, delete_auth_key_handler, generate_auth_key_handler, reload_keys_handler}; -use crate::core::Tracker; +use crate::core::authentication::handler::KeysHandler; /// It adds the routes to the router for the [`auth_key`](crate::servers::apis::v1::context::auth_key) API context. -pub fn add(prefix: &str, router: Router, tracker: Arc) -> Router { +pub fn add(prefix: &str, router: Router, keys_handler: Arc) -> Router { // Keys router .route( @@ -29,14 +29,14 @@ pub fn add(prefix: &str, router: Router, tracker: Arc) -> Router { // Use POST /keys &format!("{prefix}/key/{{seconds_valid_or_key}}"), post(generate_auth_key_handler) - .with_state(tracker.clone()) + .with_state(keys_handler.clone()) .delete(delete_auth_key_handler) - .with_state(tracker.clone()), + .with_state(keys_handler.clone()), ) // Keys command .route( &format!("{prefix}/keys/reload"), - get(reload_keys_handler).with_state(tracker.clone()), + get(reload_keys_handler).with_state(keys_handler.clone()), ) - .route(&format!("{prefix}/keys"), post(add_auth_key_handler).with_state(tracker)) + .route(&format!("{prefix}/keys"), post(add_auth_key_handler).with_state(keys_handler)) } diff --git a/src/servers/apis/v1/routes.rs b/src/servers/apis/v1/routes.rs index 1954af2e4..c26ce4f3d 100644 --- a/src/servers/apis/v1/routes.rs +++ b/src/servers/apis/v1/routes.rs @@ -5,6 +5,7 @@ use axum::Router; use tokio::sync::RwLock; use super::context::{auth_key, stats, torrent, whitelist}; +use crate::core::authentication::handler::KeysHandler; use crate::core::statistics::event::sender::Sender; use crate::core::statistics::repository::Repository; use crate::core::whitelist::manager::WhiteListManager; @@ -12,10 +13,12 @@ use crate::core::Tracker; use crate::servers::udp::server::banning::BanService; /// Add the routes for the v1 API. +#[allow(clippy::too_many_arguments)] pub fn add( prefix: &str, router: Router, tracker: Arc, + keys_handler: &Arc, whitelist_manager: &Arc, ban_service: Arc>, stats_event_sender: Arc>>, @@ -23,7 +26,7 @@ pub fn add( ) -> Router { let v1_prefix = format!("{prefix}/v1"); - let router = auth_key::routes::add(&v1_prefix, router, tracker.clone()); + let router = auth_key::routes::add(&v1_prefix, router, keys_handler.clone()); let router = stats::routes::add( &v1_prefix, router, diff --git a/src/servers/http/server.rs b/src/servers/http/server.rs index a9b618c84..5f62a2013 100644 --- a/src/servers/http/server.rs +++ b/src/servers/http/server.rs @@ -275,8 +275,8 @@ mod tests { use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; + use crate::core::whitelist; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; - use crate::core::{authentication, whitelist}; use crate::servers::http::server::{HttpServer, Launcher}; use crate::servers::registar::Registar; @@ -299,13 +299,12 @@ mod tests { let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); let authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); - let keys_handler = Arc::new(KeysHandler::new( + let _keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&keys_handler)); - let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization)); let http_trackers = cfg.http_trackers.clone().expect("missing HTTP trackers configuration"); let config = &http_trackers[0]; diff --git a/src/servers/http/v1/handlers/announce.rs b/src/servers/http/v1/handlers/announce.rs index fbadde967..c42981d4c 100644 --- a/src/servers/http/v1/handlers/announce.rs +++ b/src/servers/http/v1/handlers/announce.rs @@ -274,17 +274,12 @@ mod tests { /// Initialize tracker's dependencies and tracker. fn initialize_tracker_and_deps(config: &Configuration) -> TrackerAndDeps { - let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication_service) = initialize_tracker_dependencies(config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_event_sender = Arc::new(stats_event_sender); - let tracker = Arc::new(initialize_tracker( - config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(config, &database, &whitelist_authorization)); (tracker, stats_event_sender, whitelist_authorization, authentication_service) } diff --git a/src/servers/http/v1/handlers/scrape.rs b/src/servers/http/v1/handlers/scrape.rs index f7be42bff..de4610a61 100644 --- a/src/servers/http/v1/handlers/scrape.rs +++ b/src/servers/http/v1/handlers/scrape.rs @@ -151,13 +151,13 @@ mod tests { ) { let config = configuration::ephemeral_private(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication_service) = initialize_tracker_dependencies(&config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( - initialize_tracker(&config, &database, &whitelist_authorization, &authentication), + initialize_tracker(&config, &database, &whitelist_authorization), stats_event_sender, authentication_service, ) @@ -170,13 +170,13 @@ mod tests { ) { let config = configuration::ephemeral_listed(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication_service) = initialize_tracker_dependencies(&config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( - initialize_tracker(&config, &database, &whitelist_authorization, &authentication), + initialize_tracker(&config, &database, &whitelist_authorization), stats_event_sender, authentication_service, ) @@ -189,13 +189,13 @@ mod tests { ) { let config = configuration::ephemeral_with_reverse_proxy(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication_service) = initialize_tracker_dependencies(&config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( - initialize_tracker(&config, &database, &whitelist_authorization, &authentication), + initialize_tracker(&config, &database, &whitelist_authorization), stats_event_sender, authentication_service, ) @@ -208,13 +208,13 @@ mod tests { ) { let config = configuration::ephemeral_without_reverse_proxy(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, authentication_service) = initialize_tracker_dependencies(&config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); ( - initialize_tracker(&config, &database, &whitelist_authorization, &authentication), + initialize_tracker(&config, &database, &whitelist_authorization), stats_event_sender, authentication_service, ) diff --git a/src/servers/http/v1/services/announce.rs b/src/servers/http/v1/services/announce.rs index 2f2876f5b..018348d7e 100644 --- a/src/servers/http/v1/services/announce.rs +++ b/src/servers/http/v1/services/announce.rs @@ -73,12 +73,12 @@ mod tests { fn public_tracker() -> (Tracker, Arc>>) { let config = configuration::ephemeral_public(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_event_sender = Arc::new(stats_event_sender); - let tracker = initialize_tracker(&config, &database, &whitelist_authorization, &authentication); + let tracker = initialize_tracker(&config, &database, &whitelist_authorization); (tracker, stats_event_sender) } @@ -132,10 +132,10 @@ mod tests { fn test_tracker_factory() -> Tracker { let config = configuration::ephemeral(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - Tracker::new(&config.core, &database, &whitelist_authorization, &authentication).unwrap() + Tracker::new(&config.core, &database, &whitelist_authorization).unwrap() } #[tokio::test] diff --git a/src/servers/http/v1/services/scrape.rs b/src/servers/http/v1/services/scrape.rs index 35b264363..9ad741234 100644 --- a/src/servers/http/v1/services/scrape.rs +++ b/src/servers/http/v1/services/scrape.rs @@ -87,10 +87,10 @@ mod tests { fn public_tracker() -> Tracker { let config = configuration::ephemeral_public(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - initialize_tracker(&config, &database, &whitelist_authorization, &authentication) + initialize_tracker(&config, &database, &whitelist_authorization) } fn sample_info_hashes() -> Vec { @@ -116,10 +116,10 @@ mod tests { fn test_tracker_factory() -> Tracker { let config = configuration::ephemeral(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - Tracker::new(&config.core, &database, &whitelist_authorization, &authentication).unwrap() + Tracker::new(&config.core, &database, &whitelist_authorization).unwrap() } mod with_real_data { diff --git a/src/servers/udp/handlers.rs b/src/servers/udp/handlers.rs index f0f7719e2..feeca4e40 100644 --- a/src/servers/udp/handlers.rs +++ b/src/servers/udp/handlers.rs @@ -516,18 +516,13 @@ mod tests { } fn initialize_tracker_and_deps(config: &Configuration) -> TrackerAndDeps { - let (database, in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(config); let (stats_event_sender, _stats_repository) = statistics::setup::factory(config.core.tracker_usage_statistics); let stats_event_sender = Arc::new(stats_event_sender); let whitelist_manager = initialize_whitelist_manager(database.clone(), in_memory_whitelist.clone()); - let tracker = Arc::new(initialize_tracker( - config, - &database, - &whitelist_authorization, - &authentication, - )); + let tracker = Arc::new(initialize_tracker(config, &database, &whitelist_authorization)); ( tracker, @@ -635,10 +630,10 @@ mod tests { fn test_tracker_factory() -> (Arc, Arc) { let config = tracker_configuration(); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); - let tracker = Arc::new(Tracker::new(&config.core, &database, &whitelist_authorization, &authentication).unwrap()); + let tracker = Arc::new(Tracker::new(&config.core, &database, &whitelist_authorization).unwrap()); (tracker, whitelist_authorization) } @@ -1383,7 +1378,7 @@ mod tests { async fn the_peer_ip_should_be_changed_to_the_external_ip_in_the_tracker_configuration() { let config = Arc::new(TrackerConfigurationBuilder::default().with_external_ip("::126.0.0.1").into()); - let (database, _in_memory_whitelist, whitelist_authorization, authentication, _authentication_service) = + let (database, _in_memory_whitelist, whitelist_authorization, _authentication_service) = initialize_tracker_dependencies(&config); let mut stats_event_sender_mock = statistics::event::sender::MockSender::new(); @@ -1395,8 +1390,7 @@ mod tests { let stats_event_sender: Arc>> = Arc::new(Some(Box::new(stats_event_sender_mock))); - let tracker = - Arc::new(core::Tracker::new(&config.core, &database, &whitelist_authorization, &authentication).unwrap()); + let tracker = Arc::new(core::Tracker::new(&config.core, &database, &whitelist_authorization).unwrap()); let loopback_ipv4 = Ipv4Addr::new(127, 0, 0, 1); let loopback_ipv6 = Ipv6Addr::new(0, 0, 0, 0, 0, 0, 0, 1); diff --git a/src/servers/udp/server/mod.rs b/src/servers/udp/server/mod.rs index c507b3cb6..844c18678 100644 --- a/src/servers/udp/server/mod.rs +++ b/src/servers/udp/server/mod.rs @@ -69,8 +69,8 @@ mod tests { use crate::core::authentication::key::repository::persisted::DatabaseKeyRepository; use crate::core::authentication::service; use crate::core::services::{initialize_database, initialize_tracker, initialize_whitelist_manager, statistics}; + use crate::core::whitelist; use crate::core::whitelist::repository::in_memory::InMemoryWhitelist; - use crate::core::{authentication, whitelist}; use crate::servers::registar::Registar; use crate::servers::udp::server::banning::BanService; use crate::servers::udp::server::launcher::MAX_CONNECTION_ID_ERRORS_PER_IP; @@ -95,13 +95,12 @@ mod tests { let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); let _authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); - let keys_handler = Arc::new(KeysHandler::new( + let _keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&keys_handler)); - let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization)); let udp_trackers = cfg.udp_trackers.clone().expect("missing UDP trackers configuration"); let config = &udp_trackers[0]; @@ -148,13 +147,12 @@ mod tests { let db_key_repository = Arc::new(DatabaseKeyRepository::new(&database)); let in_memory_key_repository = Arc::new(InMemoryKeyRepository::default()); let _authentication_service = Arc::new(service::AuthenticationService::new(&cfg.core, &in_memory_key_repository)); - let keys_handler = Arc::new(KeysHandler::new( + let _keys_handler = Arc::new(KeysHandler::new( &db_key_repository.clone(), &in_memory_key_repository.clone(), )); - let authentication = Arc::new(authentication::Facade::new(&keys_handler)); - let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization, &authentication)); + let tracker = Arc::new(initialize_tracker(&cfg, &database, &whitelist_authorization)); let config = &cfg.udp_trackers.as_ref().unwrap().first().unwrap(); let bind_to = config.bind_address; diff --git a/tests/servers/api/environment.rs b/tests/servers/api/environment.rs index 3e8fedd0e..f014df36f 100644 --- a/tests/servers/api/environment.rs +++ b/tests/servers/api/environment.rs @@ -8,6 +8,7 @@ use torrust_tracker_api_client::connection_info::{ConnectionInfo, Origin}; use torrust_tracker_configuration::{Configuration, HttpApi}; use torrust_tracker_lib::bootstrap::app::{initialize_app_container, initialize_global_services}; use torrust_tracker_lib::bootstrap::jobs::make_rust_tls; +use torrust_tracker_lib::core::authentication::handler::KeysHandler; use torrust_tracker_lib::core::authentication::service::AuthenticationService; use torrust_tracker_lib::core::statistics::event::sender::Sender; use torrust_tracker_lib::core::statistics::repository::Repository; @@ -24,6 +25,7 @@ where { pub config: Arc, pub tracker: Arc, + pub keys_handler: Arc, pub authentication_service: Arc, pub stats_event_sender: Arc>>, pub stats_repository: Arc, @@ -60,6 +62,7 @@ impl Environment { Self { config, tracker: app_container.tracker.clone(), + keys_handler: app_container.keys_handler.clone(), authentication_service: app_container.authentication_service.clone(), stats_event_sender: app_container.stats_event_sender.clone(), stats_repository: app_container.stats_repository.clone(), @@ -76,6 +79,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker.clone(), + keys_handler: self.keys_handler.clone(), authentication_service: self.authentication_service.clone(), stats_event_sender: self.stats_event_sender.clone(), stats_repository: self.stats_repository.clone(), @@ -86,6 +90,7 @@ impl Environment { .server .start( self.tracker, + self.keys_handler, self.whitelist_manager, self.stats_event_sender, self.stats_repository, @@ -108,6 +113,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker, + keys_handler: self.keys_handler, authentication_service: self.authentication_service, stats_event_sender: self.stats_event_sender, stats_repository: self.stats_repository, diff --git a/tests/servers/api/v1/contract/context/auth_key.rs b/tests/servers/api/v1/contract/context/auth_key.rs index 6a270f894..73860c9c2 100644 --- a/tests/servers/api/v1/contract/context/auth_key.rs +++ b/tests/servers/api/v1/contract/context/auth_key.rs @@ -158,8 +158,7 @@ async fn should_allow_deleting_an_auth_key() { let seconds_valid = 60; let auth_key = env - .tracker - .authentication + .keys_handler .generate_auth_key(Some(Duration::from_secs(seconds_valid))) .await .unwrap(); @@ -293,8 +292,7 @@ async fn should_fail_when_the_auth_key_cannot_be_deleted() { let seconds_valid = 60; let auth_key = env - .tracker - .authentication + .keys_handler .generate_auth_key(Some(Duration::from_secs(seconds_valid))) .await .unwrap(); @@ -327,8 +325,7 @@ async fn should_not_allow_deleting_an_auth_key_for_unauthenticated_users() { // Generate new auth key let auth_key = env - .tracker - .authentication + .keys_handler .generate_auth_key(Some(Duration::from_secs(seconds_valid))) .await .unwrap(); @@ -348,8 +345,7 @@ async fn should_not_allow_deleting_an_auth_key_for_unauthenticated_users() { // Generate new auth key let auth_key = env - .tracker - .authentication + .keys_handler .generate_auth_key(Some(Duration::from_secs(seconds_valid))) .await .unwrap(); @@ -377,8 +373,7 @@ async fn should_allow_reloading_keys() { let env = Started::new(&configuration::ephemeral().into()).await; let seconds_valid = 60; - env.tracker - .authentication + env.keys_handler .generate_auth_key(Some(Duration::from_secs(seconds_valid))) .await .unwrap(); @@ -403,8 +398,7 @@ async fn should_fail_when_keys_cannot_be_reloaded() { let request_id = Uuid::new_v4(); let seconds_valid = 60; - env.tracker - .authentication + env.keys_handler .generate_auth_key(Some(Duration::from_secs(seconds_valid))) .await .unwrap(); @@ -432,8 +426,7 @@ async fn should_not_allow_reloading_keys_for_unauthenticated_users() { let env = Started::new(&configuration::ephemeral().into()).await; let seconds_valid = 60; - env.tracker - .authentication + env.keys_handler .generate_auth_key(Some(Duration::from_secs(seconds_valid))) .await .unwrap(); diff --git a/tests/servers/http/environment.rs b/tests/servers/http/environment.rs index 85921cd37..81b6a12e2 100644 --- a/tests/servers/http/environment.rs +++ b/tests/servers/http/environment.rs @@ -5,6 +5,7 @@ use futures::executor::block_on; use torrust_tracker_configuration::{Configuration, HttpTracker}; use torrust_tracker_lib::bootstrap::app::{initialize_app_container, initialize_global_services}; use torrust_tracker_lib::bootstrap::jobs::make_rust_tls; +use torrust_tracker_lib::core::authentication::handler::KeysHandler; use torrust_tracker_lib::core::authentication::service::AuthenticationService; use torrust_tracker_lib::core::statistics::event::sender::Sender; use torrust_tracker_lib::core::statistics::repository::Repository; @@ -17,6 +18,7 @@ use torrust_tracker_primitives::peer; pub struct Environment { pub config: Arc, pub tracker: Arc, + pub keys_handler: Arc, pub authentication_service: Arc, pub stats_event_sender: Arc>>, pub stats_repository: Arc, @@ -56,6 +58,7 @@ impl Environment { Self { config, tracker: app_container.tracker.clone(), + keys_handler: app_container.keys_handler.clone(), authentication_service: app_container.authentication_service.clone(), stats_event_sender: app_container.stats_event_sender.clone(), stats_repository: app_container.stats_repository.clone(), @@ -71,6 +74,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker.clone(), + keys_handler: self.keys_handler.clone(), authentication_service: self.authentication_service.clone(), whitelist_authorization: self.whitelist_authorization.clone(), stats_event_sender: self.stats_event_sender.clone(), @@ -101,6 +105,7 @@ impl Environment { Environment { config: self.config, tracker: self.tracker, + keys_handler: self.keys_handler, authentication_service: self.authentication_service, whitelist_authorization: self.whitelist_authorization, stats_event_sender: self.stats_event_sender, diff --git a/tests/servers/http/v1/contract.rs b/tests/servers/http/v1/contract.rs index d8b1c92c2..0aafbd213 100644 --- a/tests/servers/http/v1/contract.rs +++ b/tests/servers/http/v1/contract.rs @@ -1397,8 +1397,7 @@ mod configured_as_private { let env = Started::new(&configuration::ephemeral_private().into()).await; let expiring_key = env - .tracker - .authentication + .keys_handler .generate_auth_key(Some(Duration::from_secs(60))) .await .unwrap(); @@ -1547,8 +1546,7 @@ mod configured_as_private { ); let expiring_key = env - .tracker - .authentication + .keys_handler .generate_auth_key(Some(Duration::from_secs(60))) .await .unwrap();