diff --git a/Cargo.lock b/Cargo.lock index 11bb8e85..958710ee 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -160,9 +160,9 @@ checksum = "ecc7ab41815b3c653ccd2978ec3255c81349336702dfdf62ee6f7069b12a3aae" [[package]] name = "async-trait" -version = "0.1.69" +version = "0.1.73" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7b2d0f03b3640e3a630367e40c468cb7f309529c708ed1d88597047b0e7c6ef7" +checksum = "bc00ceb34980c03614e35a3a4e218276a0a824e911d07651cd0d858a51e8c0f0" dependencies = [ "proc-macro2", "quote", @@ -336,16 +336,6 @@ dependencies = [ "generic-array", ] -[[package]] -name = "bstr" -version = "1.6.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6798148dccfbff0fae41c7574d2fa8f1ef3492fba0face179de5d8d447d67b05" -dependencies = [ - "memchr", - "serde", -] - [[package]] name = "bumpalo" version = "3.13.0" @@ -709,6 +699,12 @@ dependencies = [ "parking_lot_core", ] +[[package]] +name = "data-encoding" +version = "2.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c2e66c9d817f1720209181c316d28635c050fa304f9c79e47a520882661b7308" + [[package]] name = "deranged" version = "0.3.8" @@ -1117,30 +1113,6 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b" -[[package]] -name = "globset" -version = "0.4.13" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "759c97c1e17c55525b57192c06a267cda0ac5210b222d6b82189a2338fa1c13d" -dependencies = [ - "aho-corasick", - "bstr", - "fnv", - "log", - "regex", -] - -[[package]] -name = "globwalk" -version = "0.8.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93e3af942408868f6934a7b85134a3230832b9977cf66125df2f9edcfce4ddcc" -dependencies = [ - "bitflags 1.3.2", - "ignore", - "walkdir", -] - [[package]] name = "h2" version = "0.3.21" @@ -1341,23 +1313,6 @@ dependencies = [ "unicode-normalization", ] -[[package]] -name = "ignore" -version = "0.4.20" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dbe7873dab538a9a44ad79ede1faf5f30d49f9a5c883ddbab48bce81b64b7492" -dependencies = [ - "globset", - "lazy_static", - "log", - "memchr", - "regex", - "same-file", - "thread_local", - "walkdir", - "winapi-util", -] - [[package]] name = "indexmap" version = "1.9.3" @@ -1529,12 +1484,14 @@ dependencies = [ "openssl", "pem", "pin-project", + "rand", "secrecy", "serde", "serde_json", "serde_yaml", "thiserror", "tokio", + "tokio-tungstenite", "tokio-util", "tower", "tower-http", @@ -2127,6 +2084,9 @@ dependencies = [ name = "operator-api" version = "0.1.0" dependencies = [ + "async-trait", + "k8s-openapi", + "kube", "serde", ] @@ -2233,50 +2193,6 @@ version = "2.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94" -[[package]] -name = "pest" -version = "2.7.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1acb4a4365a13f749a93f1a094a7805e5cfa0955373a9de860d962eaa3a5fe5a" -dependencies = [ - "thiserror", - "ucd-trie", -] - -[[package]] -name = "pest_derive" -version = "2.7.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "666d00490d4ac815001da55838c500eafb0320019bbaa44444137c48b443a853" -dependencies = [ - "pest", - "pest_generator", -] - -[[package]] -name = "pest_generator" -version = "2.7.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68ca01446f50dbda87c1786af8770d535423fa8a53aec03b8f4e3d7eb10e0929" -dependencies = [ - "pest", - "pest_meta", - "proc-macro2", - "quote", - "syn 2.0.23", -] - -[[package]] -name = "pest_meta" -version = "2.7.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "56af0a30af74d0445c0bf6d9d051c979b516a1a5af790d251daee76005420a48" -dependencies = [ - "once_cell", - "pest", - "sha2", -] - [[package]] name = "petgraph" version = "0.6.4" @@ -2649,15 +2565,6 @@ version = "1.0.14" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fe232bdf6be8c8de797b22184ee71118d63780ea42ac85b61d1baa6d3b782ae9" -[[package]] -name = "same-file" -version = "1.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502" -dependencies = [ - "winapi-util", -] - [[package]] name = "schemars" version = "0.8.12" @@ -2823,6 +2730,17 @@ dependencies = [ "unsafe-libyaml", ] +[[package]] +name = "sha1" +version = "0.10.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f04293dc80c3993519f2d7f6f511707ee7094fe0c6d3406feb330cdb3540eba3" +dependencies = [ + "cfg-if", + "cpufeatures", + "digest", +] + [[package]] name = "sha2" version = "0.10.7" @@ -2963,22 +2881,6 @@ dependencies = [ "windows-sys", ] -[[package]] -name = "tera" -version = "1.17.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3df578c295f9ec044ff1c829daf31bb7581d5b3c2a7a3d87419afe1f2531438c" -dependencies = [ - "globwalk", - "lazy_static", - "pest", - "pest_derive", - "regex", - "serde", - "serde_json", - "unic-segment", -] - [[package]] name = "termcolor" version = "1.2.0" @@ -3168,6 +3070,18 @@ dependencies = [ "tokio", ] +[[package]] +name = "tokio-tungstenite" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec509ac96e9a0c43427c74f003127d953a265737636129424288d27cb5c4b12c" +dependencies = [ + "futures-util", + "log", + "tokio", + "tungstenite", +] + [[package]] name = "tokio-util" version = "0.7.8" @@ -3437,66 +3351,29 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" [[package]] -name = "typenum" -version = "1.16.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba" - -[[package]] -name = "ucd-trie" -version = "0.1.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed646292ffc8188ef8ea4d1e0e0150fb15a5c2e12ad9b8fc191ae7a8a7f3c4b9" - -[[package]] -name = "unic-char-property" -version = "0.9.0" +name = "tungstenite" +version = "0.19.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a8c57a407d9b6fa02b4795eb81c5b6652060a15a7903ea981f3d723e6c0be221" +checksum = "15fba1a6d6bb030745759a9a2a588bfe8490fc8b4751a277db3a0be1c9ebbf67" dependencies = [ - "unic-char-range", -] - -[[package]] -name = "unic-char-range" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0398022d5f700414f6b899e10b8348231abf9173fa93144cbc1a43b9793c1fbc" - -[[package]] -name = "unic-common" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "80d7ff825a6a654ee85a63e80f92f054f904f21e7d12da4e22f9834a4aaa35bc" - -[[package]] -name = "unic-segment" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e4ed5d26be57f84f176157270c112ef57b86debac9cd21daaabbe56db0f88f23" -dependencies = [ - "unic-ucd-segment", -] - -[[package]] -name = "unic-ucd-segment" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2079c122a62205b421f499da10f3ee0f7697f012f55b675e002483c73ea34700" -dependencies = [ - "unic-char-property", - "unic-char-range", - "unic-ucd-version", + "byteorder", + "bytes", + "data-encoding", + "http", + "httparse", + "log", + "rand", + "sha1", + "thiserror", + "url", + "utf-8", ] [[package]] -name = "unic-ucd-version" -version = "0.9.0" +name = "typenum" +version = "1.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "96bd2f2237fe450fcd0a1d2f5f4e91711124f7857ba2e964247776ebeeb7b0c4" -dependencies = [ - "unic-common", -] +checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba" [[package]] name = "unicode-bidi" @@ -3542,6 +3419,12 @@ dependencies = [ "percent-encoding", ] +[[package]] +name = "utf-8" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" + [[package]] name = "utf8parse" version = "0.2.1" @@ -3602,16 +3485,6 @@ version = "0.9.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" -[[package]] -name = "walkdir" -version = "2.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "36df944cda56c7d8d8b7496af378e6b16de9284591917d307c9b4d313c44e698" -dependencies = [ - "same-file", - "winapi-util", -] - [[package]] name = "want" version = "0.3.1" @@ -3928,7 +3801,6 @@ dependencies = [ "futures", "serde", "serde_json", - "tera", "thiserror", "tokio", "toml 0.7.6", diff --git a/Cargo.toml b/Cargo.toml index 64463e13..f5dc833f 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,7 +1,7 @@ [workspace] members = [ + "operator-api", "operator-k8s", "sidecar", "utils", - "operator-api", ] diff --git a/assets/xline_conf.tera b/assets/xline_conf.tera deleted file mode 100644 index 19ee24a7..00000000 --- a/assets/xline_conf.tera +++ /dev/null @@ -1,17 +0,0 @@ -# Required - -[cluster] -name = "{{ name }}" -is_leader = {{ is_leader }} - -[cluster.members]{% for name, addr in members %} -{{ name }} = "{{ addr }}" -{%- endfor %} - -[storage] -engine = "{{ storage_engine }}" -data_dir = "{{ data_dir }}" - -# Additional - -{{ additional }} diff --git a/operator-api/Cargo.toml b/operator-api/Cargo.toml index 0972c217..a94f14e7 100644 --- a/operator-api/Cargo.toml +++ b/operator-api/Cargo.toml @@ -11,4 +11,7 @@ categories = ["API"] keywords = ["operator", "API", "operator"] [dependencies] +async-trait = "0.1.72" +k8s-openapi = { version = "0.18.0", features = ["v1_26", "schemars"] } +kube = { version = "0.83.0", features = ["runtime", "derive", "ws"] } serde = { version = "1.0.130", features = ["derive"] } diff --git a/operator-api/src/lib.rs b/operator-api/src/lib.rs index 1bebaa60..2070bc99 100644 --- a/operator-api/src/lib.rs +++ b/operator-api/src/lib.rs @@ -1,3 +1,6 @@ +/// Xline handle +mod xline; + use serde::{Deserialize, Serialize}; /// Heartbeat status diff --git a/operator-api/src/xline.rs b/operator-api/src/xline.rs new file mode 100644 index 00000000..2f0bf515 --- /dev/null +++ b/operator-api/src/xline.rs @@ -0,0 +1,51 @@ +use async_trait::async_trait; +use k8s_openapi::api::core::v1::Pod; +use kube::api::{AttachParams, AttachedProcess}; +use kube::Api; + +/// xline handle abstraction +#[async_trait] +pub trait XlineHandle { + /// the err during start and kill + type Err; + + /// start a xline node + async fn start(&mut self) -> Result<(), Self::Err>; + + /// kill a xline node + async fn kill(&mut self) -> Result<(), Self::Err>; +} + +/// K8s xline handle +pub struct K8sXlineHandle { + /// the pod name + pod_name: String, + /// the container name of xline + container_name: String, + /// k8s pods api + pods_api: Api, + /// the attached process of xline + process: Option, +} + +#[async_trait] +impl XlineHandle for K8sXlineHandle { + type Err = kube::Error; + + async fn start(&mut self) -> Result<(), Self::Err> { + let process = self + .pods_api + .exec( + &self.pod_name, + vec!["sh"], + &AttachParams::default().container(&self.container_name), + ) + .await?; + self.process = Some(process); + todo!() + } + + async fn kill(&mut self) -> Result<(), Self::Err> { + todo!() + } +} diff --git a/operator-k8s/Cargo.toml b/operator-k8s/Cargo.toml index 5f8d3823..3705c268 100644 --- a/operator-k8s/Cargo.toml +++ b/operator-k8s/Cargo.toml @@ -14,10 +14,15 @@ keywords = ["kubernetes", "xline", "operator"] [dependencies] anyhow = "1.0.71" async-trait = "0.1.68" +axum = "0.6.18" clap = { version = "4.3.4", features = ["derive"] } +clippy-utilities = "0.2.0" +event-listener = "2.5.3" +flume = "0.10.14" futures = "0.3.28" k8s-openapi = { version = "0.18.0", features = ["v1_26", "schemars"] } kube = { version = "0.83.0", features = ["runtime", "derive"] } +operator-api = { path = "../operator-api" } schemars = "0.8.6" serde = { version = "1.0.130", features = ["derive"] } serde_json = "1.0.97" @@ -31,11 +36,6 @@ tokio = { version = "1.0", features = [ tracing = "0.1.37" tracing-subscriber = { version = "0.3.16", features = ["env-filter"] } utils = { path = "../utils" } -axum = "0.6.18" -operator-api = { path = "../operator-api" } -flume = "0.10.14" -clippy-utilities = "0.2.0" -event-listener = "2.5.3" [dev-dependencies] garde = { version = "0.11.2", default-features = false, features = ["derive", "pattern"] } diff --git a/sidecar/Cargo.toml b/sidecar/Cargo.toml index 97d44b88..22fe675d 100644 --- a/sidecar/Cargo.toml +++ b/sidecar/Cargo.toml @@ -22,13 +22,12 @@ event-listener = "2.5.3" futures = "0.3.28" serde = { version = "1.0.130", features = ["derive"] } serde_json = "1.0.97" -tera = { version = "1.17.1", default-features = false } thiserror = "1.0.40" tokio = { version = "1.0", features = [ - "rt-multi-thread", - "time", - "macros", - "net", + "rt-multi-thread", + "time", + "macros", + "net", ] } toml = "0.7.4" tonic = "0.9.2" diff --git a/sidecar/src/main.rs b/sidecar/src/main.rs index bb764745..94ea3c0e 100644 --- a/sidecar/src/main.rs +++ b/sidecar/src/main.rs @@ -136,13 +136,10 @@ )] use std::collections::HashMap; -use std::fs::write; use std::path::PathBuf; -use std::time::Duration; use anyhow::{anyhow, Result}; -use clap::{Parser, Subcommand}; -use tera::{Context, Tera}; +use clap::Parser; use tracing::debug; use xline_sidecar::operator::Operator; @@ -155,57 +152,78 @@ struct Cli { /// The name of this node #[arg(long)] name: String, // used in xline and deployment operator to identify this node - /// The host ip of each member, [node_name] -> [node_host] #[arg(long, value_parser = parse_members)] members: HashMap, - /// The xline server port #[arg(long)] xline_port: u16, - - /// Sub commands - #[command(subcommand)] - command: Commands, + /// Operator web server port + #[arg(long)] + operator_port: u16, + /// The xline container name + #[arg(long)] + container_name: String, + /// Check health interval, default 20 [unit: seconds] + #[arg(long, default_value = "20")] + check_interval: u64, + /// Enable backup, choose a storage type, e.g. s3:bucket_name or pv:/path/to/dir + #[arg(long, value_parser=parse_backup_type)] + backup: Option, + /// The xline executable path, default "xline" + #[arg(long, default_value = "xline")] + xline_executable: String, + /// Storage engine used in xline + #[arg(long)] + storage_engine: String, + /// The directory path contains xline server data if the storage_engine is rocksdb + #[arg(long)] + data_dir: PathBuf, + /// Whether this node is leader or not + #[arg(long, default_value = "false")] + is_leader: bool, + /// Additional arguments, it will be appended behind the required parameters, + /// e.g "--jaeger_offline true" + #[arg(long)] + additional: Option, } -/// Sub commands -#[allow(variant_size_differences)] // required by clap -#[derive(Subcommand, Debug)] -enum Commands { - /// Run sidecar operator - Run { - /// The xline container name - #[arg(long)] - container_name: String, - /// Operator web server port - #[arg(long)] - operator_port: u16, - /// Check health interval, default 20 [unit: seconds] - #[arg(long, default_value = "20")] - check_interval: u64, - /// Enable backup, choose a storage type, e.g. s3:bucket_name:secret_key or pv:/path/to/dir - #[arg(long, value_parser=parse_backup_type)] - backup: Option, - }, - /// Generate xline configuration file - Gen { - /// The file path where the xline kvserver reads configs - #[arg(long)] - path: PathBuf, - /// Storage engine used in xline - #[arg(long)] - storage_engine: String, - /// The directory path contains xline kvserver data is the storage_engine is rocksdb - #[arg(long)] - data_dir: PathBuf, - /// Whether this node is leader or not - #[arg(long)] - is_leader: bool, - /// Additional arguments [format: JSON] - #[arg(long)] - additional: Option, - }, +impl From for Config { + fn from(value: Cli) -> Self { + let mut config = Self { + start_cmd: String::new(), + name: value.name.clone(), + container_name: value.container_name, + xline_port: value.xline_port, + operator_port: value.operator_port, + check_interval: std::time::Duration::from_secs(value.check_interval), + backup: value.backup, + members: value.members, + }; + config.start_cmd = format!( + "{} --name {} --members {} --storage-engine {} --data-dir {}", + value.xline_executable, + value.name, + config + .xline_members() + .into_iter() + .map(|(name, addr)| format!("{name}={addr}")) + .collect::>() + .join(","), + value.storage_engine, + value.data_dir.to_string_lossy(), + ); + if value.is_leader { + config.start_cmd.push(' '); + config.start_cmd.push_str("--is-leader"); + } + if let Some(additional) = value.additional { + config.start_cmd.push(' '); + let pat: &[_] = &['\'', '"']; + config.start_cmd.push_str(additional.trim_matches(pat)); + } + config + } } /// parse backup type @@ -218,7 +236,7 @@ fn parse_backup_type(value: &str) -> Result { let backup_type = items.remove(0); match backup_type { "s3" => { - if items.len() != 2 { + if items.len() != 1 { return Err(format!( "s3 backup type requires 1 arguments, got {}", items.len() @@ -262,9 +280,6 @@ pub fn parse_members(s: &str) -> Result> { Ok(map) } -/// Xline config template -pub static XLINE_CONF: &str = include_str!("../../assets/xline_conf.tera"); - #[tokio::main] async fn main() -> Result<()> { tracing_subscriber::fmt::init(); @@ -272,53 +287,68 @@ async fn main() -> Result<()> { let cli = Cli::parse(); debug!("{:?}", cli); - match cli.command { - Commands::Run { - container_name, - operator_port, - check_interval, - backup, - } => { - let config = Config::new( - cli.name, - container_name, - cli.members, - cli.xline_port, - operator_port, - Duration::from_secs(check_interval), - backup, - ); - Operator::new(config).run().await - } - Commands::Gen { - path, - storage_engine, - data_dir, - is_leader, - additional, - } => { - let mut ctx = Context::new(); - let members: HashMap<_, _> = cli - .members - .into_iter() - .map(|(node_name, host)| (node_name, format!("{host}:{}", cli.xline_port))) - .collect(); - ctx.insert("name", &cli.name); - ctx.insert("is_leader", &is_leader); - ctx.insert("members", &members); - ctx.insert("storage_engine", &storage_engine); - ctx.insert("data_dir", &data_dir); - let additional = if let Some(json) = additional.as_deref() { - let value: serde_json::Value = serde_json::from_str(json)?; - toml::to_string_pretty(&value)? - } else { - String::new() - }; - ctx.insert("additional", &additional); - let conf = Tera::one_off(XLINE_CONF, &ctx, false)?; - debug!("generate config: \n{}", conf); - write(path, conf)?; - Ok(()) - } + Operator::new(cli.into()).run().await +} + +#[cfg(test)] +mod test { + use crate::Cli; + use clap::Parser; + use std::collections::HashMap; + use xline_sidecar::types::{Backup, Config}; + + fn full_parameter() -> Vec<&'static str> { + vec![ + "sidecar_exe", + "--name=node1", + "--members=node1=127.0.0.1", + "--xline-port=2379", + "--operator-port=2380", + "--container-name=xline", + "--check-interval=60", + "--backup=s3:bucket_name", + "--xline-executable=/usr/local/bin/xline", + "--storage-engine=rocksdb", + "--data-dir=/usr/local/xline/data-dir", + "--is-leader", + "--additional='--auth-public-key /mnt/public.pem --auth-private-key /mnt/private.pem'", + ] + } + + #[test] + fn test_parse_cli_should_success() { + let cli = Cli::parse_from(full_parameter()); + assert_eq!(cli.name, "node1"); + assert_eq!( + cli.members, + HashMap::from([("node1".to_owned(), "127.0.0.1".to_owned())]) + ); + assert_eq!(cli.xline_port, 2379); + assert_eq!(cli.operator_port, 2380); + assert_eq!(cli.container_name, "xline"); + assert_eq!(cli.check_interval, 60); + assert_eq!( + cli.backup, + Some(Backup::S3 { + bucket: "bucket_name".to_owned(), + }) + ); + assert_eq!(cli.xline_executable, "/usr/local/bin/xline"); + assert_eq!(cli.storage_engine, "rocksdb"); + assert_eq!(cli.data_dir.to_string_lossy(), "/usr/local/xline/data-dir"); + assert!(cli.is_leader); + assert_eq!( + cli.additional, + Some( + "'--auth-public-key /mnt/public.pem --auth-private-key /mnt/private.pem'" + .to_owned() + ) + ); + } + + #[test] + fn test_gen_start_cmd() { + let config: Config = Cli::parse_from(full_parameter()).into(); + assert_eq!(config.start_cmd, "/usr/local/bin/xline --name node1 --members node1=127.0.0.1:2379 --storage-engine rocksdb --data-dir /usr/local/xline/data-dir --is-leader --auth-public-key /mnt/public.pem --auth-private-key /mnt/private.pem"); } } diff --git a/sidecar/src/types.rs b/sidecar/src/types.rs index 77e35669..87887f85 100644 --- a/sidecar/src/types.rs +++ b/sidecar/src/types.rs @@ -7,7 +7,7 @@ use std::time::Duration; /// Sidecar operator config #[derive(Debug, Clone)] -#[non_exhaustive] +#[allow(clippy::exhaustive_structs)] // it is exhaustive pub struct Config { /// Name of this node pub name: String, @@ -22,11 +22,13 @@ pub struct Config { /// Backup storage config pub backup: Option, /// Operators hosts, [pod_name]->[pod_host] - members: HashMap, + pub members: HashMap, + /// The xline start cmd + pub start_cmd: String, } /// Backup storage config -#[derive(Debug, Clone)] +#[derive(Debug, Clone, PartialEq, Eq)] #[non_exhaustive] pub enum Backup { /// S3 storage @@ -42,31 +44,10 @@ pub enum Backup { } impl Config { - /// Constructor + /// Get the operator members #[must_use] #[inline] - pub fn new( - name: String, - container_name: String, - members: HashMap, - xline_port: u16, - operator_port: u16, - check_interval: Duration, - backup: Option, - ) -> Self { - Self { - name, - container_name, - xline_port, - operator_port, - check_interval, - backup, - members, - } - } - - /// Get the operator members - pub(crate) fn operator_members(&self) -> HashMap { + pub fn operator_members(&self) -> HashMap { self.members .clone() .into_iter() @@ -75,7 +56,9 @@ impl Config { } /// Get the xline members - pub(crate) fn xline_members(&self) -> HashMap { + #[must_use] + #[inline] + pub fn xline_members(&self) -> HashMap { self.members .clone() .into_iter()