From 287e48422003e2e1b890dd2de9cb5ce102601d8c Mon Sep 17 00:00:00 2001 From: Jose Celano Date: Fri, 2 Aug 2024 10:21:00 +0100 Subject: [PATCH] feat!: [#958] improve metadata in config files The metadata section in the configuration file is changed: TOML: ```toml [metadata] app = "torrust-tracker" purpose = "configuration" schema_version = "2.0.0" ``` JSON: ```json { "metadata": { "app": "torrust-tracker", "purpose": "configuration", "version": "2.0.0" } } ``` - `app`: the applications this config file is used for. - `purpose`: the purpose of the file containing these metadata. - `schema_version`: the schema version for the file being parsed. --- packages/configuration/src/lib.rs | 71 ++++++++++++++----- .../configuration/src/{v2 => v2_0_0}/core.rs | 16 ++--- .../src/{v2 => v2_0_0}/database.rs | 0 .../src/{v2 => v2_0_0}/health_check_api.rs | 0 .../src/{v2 => v2_0_0}/http_tracker.rs | 0 .../src/{v2 => v2_0_0}/logging.rs | 0 .../configuration/src/{v2 => v2_0_0}/mod.rs | 14 ++-- .../src/{v2 => v2_0_0}/network.rs | 0 .../src/{v2 => v2_0_0}/tracker_api.rs | 2 +- .../src/{v2 => v2_0_0}/udp_tracker.rs | 0 .../config/tracker.container.mysql.toml | 5 +- .../config/tracker.container.sqlite3.toml | 5 +- .../config/tracker.development.sqlite3.toml | 5 +- .../config/tracker.e2e.container.sqlite3.toml | 5 +- .../config/tracker.udp.benchmarking.toml | 5 +- src/bootstrap/config.rs | 2 +- src/core/mod.rs | 6 +- 17 files changed, 93 insertions(+), 43 deletions(-) rename packages/configuration/src/{v2 => v2_0_0}/core.rs (90%) rename packages/configuration/src/{v2 => v2_0_0}/database.rs (100%) rename packages/configuration/src/{v2 => v2_0_0}/health_check_api.rs (100%) rename packages/configuration/src/{v2 => v2_0_0}/http_tracker.rs (100%) rename packages/configuration/src/{v2 => v2_0_0}/logging.rs (100%) rename packages/configuration/src/{v2 => v2_0_0}/mod.rs (97%) rename packages/configuration/src/{v2 => v2_0_0}/network.rs (100%) rename packages/configuration/src/{v2 => v2_0_0}/tracker_api.rs (98%) rename packages/configuration/src/{v2 => v2_0_0}/udp_tracker.rs (100%) diff --git a/packages/configuration/src/lib.rs b/packages/configuration/src/lib.rs index 7b59d3f95..aedf3a6f1 100644 --- a/packages/configuration/src/lib.rs +++ b/packages/configuration/src/lib.rs @@ -4,7 +4,7 @@ //! Torrust Tracker, which is a `BitTorrent` tracker server. //! //! The current version for configuration is [`v2`]. -pub mod v2; +pub mod v2_0_0; pub mod validator; use std::collections::HashMap; @@ -35,53 +35,86 @@ const ENV_VAR_CONFIG_TOML: &str = "TORRUST_TRACKER_CONFIG_TOML"; /// The `tracker.toml` file location. pub const ENV_VAR_CONFIG_TOML_PATH: &str = "TORRUST_TRACKER_CONFIG_TOML_PATH"; -pub type Configuration = v2::Configuration; -pub type Core = v2::core::Core; -pub type HealthCheckApi = v2::health_check_api::HealthCheckApi; -pub type HttpApi = v2::tracker_api::HttpApi; -pub type HttpTracker = v2::http_tracker::HttpTracker; -pub type UdpTracker = v2::udp_tracker::UdpTracker; -pub type Database = v2::database::Database; -pub type Driver = v2::database::Driver; -pub type Threshold = v2::logging::Threshold; +pub type Configuration = v2_0_0::Configuration; +pub type Core = v2_0_0::core::Core; +pub type HealthCheckApi = v2_0_0::health_check_api::HealthCheckApi; +pub type HttpApi = v2_0_0::tracker_api::HttpApi; +pub type HttpTracker = v2_0_0::http_tracker::HttpTracker; +pub type UdpTracker = v2_0_0::udp_tracker::UdpTracker; +pub type Database = v2_0_0::database::Database; +pub type Driver = v2_0_0::database::Driver; +pub type Threshold = v2_0_0::logging::Threshold; pub type AccessTokens = HashMap; -pub const LATEST_VERSION: &str = "2"; +pub const LATEST_VERSION: &str = "2.0.0"; /// Info about the configuration specification. #[derive(Serialize, Deserialize, PartialEq, Eq, Debug, Display, Clone)] +#[display(fmt = "Metadata(app: {app}, purpose: {purpose}, schema_version: {schema_version})")] pub struct Metadata { - #[serde(default = "Metadata::default_version")] + /// The application this configuration is valid for. + #[serde(default = "Metadata::default_app")] + app: App, + + /// The purpose of this parsed file. + #[serde(default = "Metadata::default_purpose")] + purpose: Purpose, + + /// The schema version for the configuration. + #[serde(default = "Metadata::default_schema_version")] #[serde(flatten)] - version: Version, + schema_version: Version, } impl Default for Metadata { fn default() -> Self { Self { - version: Self::default_version(), + app: Self::default_app(), + purpose: Self::default_purpose(), + schema_version: Self::default_schema_version(), } } } impl Metadata { - fn default_version() -> Version { + fn default_app() -> App { + App::TorrustTracker + } + + fn default_purpose() -> Purpose { + Purpose::Configuration + } + + fn default_schema_version() -> Version { Version::latest() } } +#[derive(Serialize, Deserialize, PartialEq, Eq, Debug, Display, Clone)] +#[serde(rename_all = "kebab-case")] +pub enum App { + TorrustTracker, +} + +#[derive(Serialize, Deserialize, PartialEq, Eq, Debug, Display, Clone)] +#[serde(rename_all = "lowercase")] +pub enum Purpose { + Configuration, +} + /// The configuration version. #[derive(Serialize, Deserialize, PartialEq, Eq, Debug, Display, Clone)] +#[serde(rename_all = "lowercase")] pub struct Version { #[serde(default = "Version::default_semver")] - version: String, + schema_version: String, } impl Default for Version { fn default() -> Self { Self { - version: Self::default_semver(), + schema_version: Self::default_semver(), } } } @@ -89,13 +122,13 @@ impl Default for Version { impl Version { fn new(semver: &str) -> Self { Self { - version: semver.to_owned(), + schema_version: semver.to_owned(), } } fn latest() -> Self { Self { - version: LATEST_VERSION.to_string(), + schema_version: LATEST_VERSION.to_string(), } } diff --git a/packages/configuration/src/v2/core.rs b/packages/configuration/src/v2_0_0/core.rs similarity index 90% rename from packages/configuration/src/v2/core.rs rename to packages/configuration/src/v2_0_0/core.rs index 3dfde122e..ed3e6aeb7 100644 --- a/packages/configuration/src/v2/core.rs +++ b/packages/configuration/src/v2_0_0/core.rs @@ -2,18 +2,18 @@ use derive_more::{Constructor, Display}; use serde::{Deserialize, Serialize}; use super::network::Network; -use crate::v2::database::Database; +use crate::v2_0_0::database::Database; use crate::validator::{SemanticValidationError, Validator}; use crate::{AnnouncePolicy, TrackerPolicy}; #[allow(clippy::struct_excessive_bools)] #[derive(Serialize, Deserialize, PartialEq, Eq, Debug, Clone)] pub struct Core { - // Announce policy configuration. + /// Announce policy configuration. #[serde(default = "Core::default_announce_policy")] pub announce_policy: AnnouncePolicy, - // Database configuration. + /// Database configuration. #[serde(default = "Core::default_database")] pub database: Database, @@ -22,23 +22,23 @@ pub struct Core { #[serde(default = "Core::default_inactive_peer_cleanup_interval")] pub inactive_peer_cleanup_interval: u64, - // When `true` only approved torrents can be announced in the tracker. + /// When `true` only approved torrents can be announced in the tracker. #[serde(default = "Core::default_listed")] pub listed: bool, - // Network configuration. + /// Network configuration. #[serde(default = "Core::default_network")] pub net: Network, - // When `true` clients require a key to connect and use the tracker. + /// When `true` clients require a key to connect and use the tracker. #[serde(default = "Core::default_private")] pub private: bool, - // Configuration specific when the tracker is running in private mode. + /// Configuration specific when the tracker is running in private mode. #[serde(default = "Core::default_private_mode")] pub private_mode: Option, - // Tracker policy configuration. + /// Tracker policy configuration. #[serde(default = "Core::default_tracker_policy")] pub tracker_policy: TrackerPolicy, diff --git a/packages/configuration/src/v2/database.rs b/packages/configuration/src/v2_0_0/database.rs similarity index 100% rename from packages/configuration/src/v2/database.rs rename to packages/configuration/src/v2_0_0/database.rs diff --git a/packages/configuration/src/v2/health_check_api.rs b/packages/configuration/src/v2_0_0/health_check_api.rs similarity index 100% rename from packages/configuration/src/v2/health_check_api.rs rename to packages/configuration/src/v2_0_0/health_check_api.rs diff --git a/packages/configuration/src/v2/http_tracker.rs b/packages/configuration/src/v2_0_0/http_tracker.rs similarity index 100% rename from packages/configuration/src/v2/http_tracker.rs rename to packages/configuration/src/v2_0_0/http_tracker.rs diff --git a/packages/configuration/src/v2/logging.rs b/packages/configuration/src/v2_0_0/logging.rs similarity index 100% rename from packages/configuration/src/v2/logging.rs rename to packages/configuration/src/v2_0_0/logging.rs diff --git a/packages/configuration/src/v2/mod.rs b/packages/configuration/src/v2_0_0/mod.rs similarity index 97% rename from packages/configuration/src/v2/mod.rs rename to packages/configuration/src/v2_0_0/mod.rs index de8af0891..b426b5c03 100644 --- a/packages/configuration/src/v2/mod.rs +++ b/packages/configuration/src/v2_0_0/mod.rs @@ -255,7 +255,7 @@ use crate::validator::{SemanticValidationError, Validator}; use crate::{Error, Info, Metadata, Version}; /// This configuration version -const VERSION_2: &str = "2"; +const VERSION_2_0_0: &str = "2.0.0"; /// Prefix for env vars that overwrite configuration options. const CONFIG_OVERRIDE_PREFIX: &str = "TORRUST_TRACKER_CONFIG_OVERRIDE_"; @@ -267,7 +267,6 @@ const CONFIG_OVERRIDE_SEPARATOR: &str = "__"; #[derive(Serialize, Deserialize, PartialEq, Eq, Debug, Default, Clone)] pub struct Configuration { /// Configuration metadata. - #[serde(flatten)] pub metadata: Metadata, /// Logging configuration @@ -335,9 +334,9 @@ impl Configuration { let config: Configuration = figment.extract()?; - if config.metadata.version != Version::new(VERSION_2) { + if config.metadata.schema_version != Version::new(VERSION_2_0_0) { return Err(Error::UnsupportedVersion { - version: config.metadata.version, + version: config.metadata.schema_version, }); } @@ -406,12 +405,15 @@ mod tests { use std::net::{IpAddr, Ipv4Addr}; - use crate::v2::Configuration; + use crate::v2_0_0::Configuration; use crate::Info; #[cfg(test)] fn default_config_toml() -> String { - let config = r#"version = "2" + let config = r#"[metadata] + app = "torrust-tracker" + purpose = "configuration" + schema_version = "2.0.0" [logging] threshold = "info" diff --git a/packages/configuration/src/v2/network.rs b/packages/configuration/src/v2_0_0/network.rs similarity index 100% rename from packages/configuration/src/v2/network.rs rename to packages/configuration/src/v2_0_0/network.rs diff --git a/packages/configuration/src/v2/tracker_api.rs b/packages/configuration/src/v2_0_0/tracker_api.rs similarity index 98% rename from packages/configuration/src/v2/tracker_api.rs rename to packages/configuration/src/v2_0_0/tracker_api.rs index dbbff7995..43b08a21e 100644 --- a/packages/configuration/src/v2/tracker_api.rs +++ b/packages/configuration/src/v2_0_0/tracker_api.rs @@ -71,7 +71,7 @@ impl HttpApi { #[cfg(test)] mod tests { - use crate::v2::tracker_api::HttpApi; + use crate::v2_0_0::tracker_api::HttpApi; #[test] fn http_api_configuration_should_check_if_it_contains_a_token() { diff --git a/packages/configuration/src/v2/udp_tracker.rs b/packages/configuration/src/v2_0_0/udp_tracker.rs similarity index 100% rename from packages/configuration/src/v2/udp_tracker.rs rename to packages/configuration/src/v2_0_0/udp_tracker.rs diff --git a/share/default/config/tracker.container.mysql.toml b/share/default/config/tracker.container.mysql.toml index 1c84fb2e2..1fcad4df1 100644 --- a/share/default/config/tracker.container.mysql.toml +++ b/share/default/config/tracker.container.mysql.toml @@ -1,4 +1,7 @@ -version = "2" +[metadata] +app = "torrust-tracker" +purpose = "configuration" +schema_version = "2.0.0" [core.database] driver = "mysql" diff --git a/share/default/config/tracker.container.sqlite3.toml b/share/default/config/tracker.container.sqlite3.toml index aa8aefa5e..017df5b48 100644 --- a/share/default/config/tracker.container.sqlite3.toml +++ b/share/default/config/tracker.container.sqlite3.toml @@ -1,4 +1,7 @@ -version = "2" +[metadata] +app = "torrust-tracker" +purpose = "configuration" +schema_version = "2.0.0" [core.database] path = "/var/lib/torrust/tracker/database/sqlite3.db" diff --git a/share/default/config/tracker.development.sqlite3.toml b/share/default/config/tracker.development.sqlite3.toml index 554835922..1ecc76532 100644 --- a/share/default/config/tracker.development.sqlite3.toml +++ b/share/default/config/tracker.development.sqlite3.toml @@ -1,4 +1,7 @@ -version = "2" +[metadata] +app = "torrust-tracker" +purpose = "configuration" +schema_version = "2.0.0" [[udp_trackers]] bind_address = "0.0.0.0:6969" diff --git a/share/default/config/tracker.e2e.container.sqlite3.toml b/share/default/config/tracker.e2e.container.sqlite3.toml index 6b1383fb5..7c6f4bb77 100644 --- a/share/default/config/tracker.e2e.container.sqlite3.toml +++ b/share/default/config/tracker.e2e.container.sqlite3.toml @@ -1,4 +1,7 @@ -version = "2" +[metadata] +app = "torrust-tracker" +purpose = "configuration" +schema_version = "2.0.0" [core.database] path = "/var/lib/torrust/tracker/database/sqlite3.db" diff --git a/share/default/config/tracker.udp.benchmarking.toml b/share/default/config/tracker.udp.benchmarking.toml index 907a05456..afbef84b8 100644 --- a/share/default/config/tracker.udp.benchmarking.toml +++ b/share/default/config/tracker.udp.benchmarking.toml @@ -1,4 +1,7 @@ -version = "2" +[metadata] +app = "torrust-tracker" +purpose = "configuration" +schema_version = "2.0.0" [logging] threshold = "error" diff --git a/src/bootstrap/config.rs b/src/bootstrap/config.rs index 6b607bd6f..fb5afe403 100644 --- a/src/bootstrap/config.rs +++ b/src/bootstrap/config.rs @@ -24,7 +24,7 @@ pub const DEFAULT_PATH_CONFIG: &str = "./share/default/config/tracker.developmen #[must_use] pub fn initialize_configuration() -> Configuration { let info = Info::new(DEFAULT_PATH_CONFIG.to_string()).expect("info to load configuration is not valid"); - Configuration::load(&info).expect("configuration should be loaded from provided info") + Configuration::load(&info).expect("error loading configuration from sources") } #[cfg(test)] diff --git a/src/core/mod.rs b/src/core/mod.rs index ea1472b61..98de9e4fd 100644 --- a/src/core/mod.rs +++ b/src/core/mod.rs @@ -459,7 +459,7 @@ use derive_more::Constructor; use error::PeerKeyError; use tokio::sync::mpsc::error::SendError; use torrust_tracker_clock::clock::Time; -use torrust_tracker_configuration::v2::database; +use torrust_tracker_configuration::v2_0_0::database; use torrust_tracker_configuration::{AnnouncePolicy, Core, TORRENT_PEERS_LIMIT}; use torrust_tracker_located_error::Located; use torrust_tracker_primitives::info_hash::InfoHash; @@ -1841,7 +1841,7 @@ mod tests { use std::time::Duration; use torrust_tracker_clock::clock::Time; - use torrust_tracker_configuration::v2::core::PrivateMode; + use torrust_tracker_configuration::v2_0_0::core::PrivateMode; use crate::core::auth::Key; use crate::core::tests::the_tracker::private_tracker; @@ -1893,7 +1893,7 @@ mod tests { use std::time::Duration; use torrust_tracker_clock::clock::Time; - use torrust_tracker_configuration::v2::core::PrivateMode; + use torrust_tracker_configuration::v2_0_0::core::PrivateMode; use crate::core::auth::Key; use crate::core::tests::the_tracker::private_tracker;