diff --git a/.gitignore b/.gitignore index 3ad07a5..cca6749 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,7 @@ /*.tar.gz /app_packages /config +/data /ptth_server.toml /ptth_relay.toml /ptth_build_L6KLMVS6/ diff --git a/crates/ptth_relay/src/config.rs b/crates/ptth_relay/src/config.rs index 451d130..9ff2751 100644 --- a/crates/ptth_relay/src/config.rs +++ b/crates/ptth_relay/src/config.rs @@ -30,19 +30,31 @@ pub mod machine_editable { use super::file::Server; - #[derive (Deserialize, Serialize)] + #[derive (Default, Deserialize, Serialize)] pub struct Config { pub servers: Vec , + pub debug_toggle: bool, } impl Config { - pub async fn from_file (path: &Path) -> Result + pub fn from_file (path: &Path) -> Result { - let config_s = tokio::fs::read_to_string (path).await?; + let config_s = std::fs::read_to_string (path)?; let new_config: Config = toml::from_str (&config_s)?; Ok (new_config) } + + pub async fn save (&self, path: &Path) -> Result <(), crate::ConfigError> { + let s = toml::to_string (self)?; + // This is way easier in C++ but also not safe + let mut temp_path = path.file_name ().unwrap ().to_os_string (); + temp_path.push (".partial"); + let temp_path = path.with_file_name (temp_path); + tokio::fs::write (&temp_path, &s).await?; + tokio::fs::rename (&temp_path, path).await?; + Ok (()) + } } } diff --git a/crates/ptth_relay/src/errors.rs b/crates/ptth_relay/src/errors.rs index 9e16573..c25aaca 100644 --- a/crates/ptth_relay/src/errors.rs +++ b/crates/ptth_relay/src/errors.rs @@ -20,6 +20,9 @@ pub enum ConfigError { #[error ("Bad server address")] BadServerAddress, + #[error (transparent)] + TomlSerialization (#[from] toml::ser::Error), + #[error ("unknown config error")] Unknown, } diff --git a/crates/ptth_relay/src/lib.rs b/crates/ptth_relay/src/lib.rs index 7fd0d06..0c1a49a 100644 --- a/crates/ptth_relay/src/lib.rs +++ b/crates/ptth_relay/src/lib.rs @@ -542,13 +542,36 @@ async fn handle_all ( ClientServerList => handle_server_list (state, handlebars).await?, ClientUnregisteredServers => handle_unregistered_servers (state, handlebars).await?, Debug => { - let s = handlebars.render ("debug", &())?; + #[derive (Serialize)] + struct DebugPage { + persistent_toggle: bool, + } + + let page; + + { + let guard = state.me_config.read ().await; + page = DebugPage { + persistent_toggle: guard.debug_toggle, + }; + } + + let s = handlebars.render ("debug", &page)?; ok_reply (s)? }, DebugEndlessSink => handle_endless_sink (req).await?, DebugEndlessSource (throttle) => handle_endless_source (1, throttle).await?, DebugGenKey => handle_gen_scraper_key (state).await?, DebugMysteriousError => return Err (RequestError::Mysterious), + DebugToggle => { + trace! ("Toggling debug toggle"); + { + let mut guard = state.me_config.write ().await; + guard.debug_toggle = ! guard.debug_toggle; + guard.save (Path::new ("data/ptth_relay_me_config.toml")).await.unwrap (); + } + error_reply (StatusCode::OK, "Toggled.")? + }, ErrorBadUriFormat => error_reply (StatusCode::BAD_REQUEST, "Bad URI format")?, ErrorCantPost => { error! ("Can't POST {}", path); @@ -613,7 +636,7 @@ async fn reload_config ( let new_config = Config::from_file (config_reload_path).await?; // Reload machine-editable config, if possible - let me_config = machine_editable::Config::from_file (Path::new ("data/ptth_relay_me_config.toml")).await.ok (); + // let me_config = machine_editable::Config::from_file (Path::new ("data/ptth_relay_me_config.toml")).await.ok (); let mut config = state.config.write ().await; diff --git a/crates/ptth_relay/src/relay_state.rs b/crates/ptth_relay/src/relay_state.rs index 037b83c..e639a5c 100644 --- a/crates/ptth_relay/src/relay_state.rs +++ b/crates/ptth_relay/src/relay_state.rs @@ -1,6 +1,7 @@ use std::{ collections::HashMap, convert::TryFrom, + path::Path, time::Instant, }; @@ -18,6 +19,7 @@ use crate::{ Config, RelayError, ShuttingDownError, + config::machine_editable, }; use ptth_core::{ @@ -76,6 +78,7 @@ impl Default for ServerStatus { pub struct Relay { pub (crate) config: RwLock , + pub (crate) me_config: RwLock , /// The parked clients or parked server, keyed by server @@ -170,8 +173,20 @@ impl TryFrom for Relay { fn try_from (config: Config) -> Result { let (shutdown_watch_tx, shutdown_watch_rx) = watch::channel (false); + let me_config = machine_editable::Config::default (); + + let me_config = match machine_editable::Config::from_file (Path::new ("data/ptth_relay_me_config.toml")) + { + Err (e) => { + error! ("Can't load machine-editable config: {:?}", e); + me_config + }, + Ok (x) => x, + }; + Ok (Self { config: config.into (), + me_config: me_config.into (), request_rendezvous: Default::default (), server_status: Default::default (), response_rendezvous: Default::default (), diff --git a/crates/ptth_relay/src/routing.rs b/crates/ptth_relay/src/routing.rs index 352debb..60b72b4 100644 --- a/crates/ptth_relay/src/routing.rs +++ b/crates/ptth_relay/src/routing.rs @@ -15,6 +15,7 @@ pub enum Route <'a> { DebugEndlessSource (Option ), DebugGenKey, DebugMysteriousError, + DebugToggle, ErrorBadUriFormat, ErrorCantPost, ErrorMethodNotAllowed, @@ -41,6 +42,9 @@ pub fn route_url <'a> (method: &Method, path: &'a str) -> Route <'a> { else if path == "/frontend/debug/endless_sink" { Route::DebugEndlessSink } + else if path == "/frontend/debug/toggle" { + Route::DebugToggle + } else { Route::ErrorCantPost } diff --git a/handlebars/relay/debug.hbs b/handlebars/relay/debug.hbs index 2b97b3f..f89e422 100644 --- a/handlebars/relay/debug.hbs +++ b/handlebars/relay/debug.hbs @@ -52,5 +52,11 @@ Lorem ipsum dolor set amet

Data sink (POST only) +

Persistent toggle is

{{persistent_toggle}}

+ +
+ +
+