mithril_client_cli/
command_context.rs

1use anyhow::anyhow;
2use slog::Logger;
3
4use mithril_client::MithrilResult;
5
6use crate::configuration::ConfigParameters;
7
8/// Context for the command execution
9pub struct CommandContext {
10    config_parameters: ConfigParameters,
11    unstable_enabled: bool,
12    json: bool,
13    logger: Logger,
14}
15
16impl CommandContext {
17    /// Create a new command context
18    pub fn new(
19        config_parameters: ConfigParameters,
20        unstable_enabled: bool,
21        json: bool,
22        logger: Logger,
23    ) -> Self {
24        Self {
25            config_parameters,
26            unstable_enabled,
27            json,
28            logger,
29        }
30    }
31
32    /// Check if unstable commands are enabled
33    pub fn is_unstable_enabled(&self) -> bool {
34        self.unstable_enabled
35    }
36
37    /// Check if JSON output is enabled
38    pub fn is_json_output_enabled(&self) -> bool {
39        self.json
40    }
41
42    /// Ensure that unstable commands are enabled
43    pub fn require_unstable(
44        &self,
45        sub_command: &str,
46        command_example: Option<&str>,
47    ) -> MithrilResult<()> {
48        if self.is_unstable_enabled() {
49            Ok(())
50        } else {
51            let example = command_example.map(|e| format!(" {e}")).unwrap_or_default();
52            Err(anyhow!(
53                "The \"{sub_command}\" subcommand is only accepted using the --unstable flag.\n\n\
54                ie: \"mithril-client --unstable {sub_command}{example}\""
55            ))
56        }
57    }
58
59    /// Get a reference to the configured parameters
60    pub fn config_parameters(&self) -> &ConfigParameters {
61        &self.config_parameters
62    }
63
64    /// Get a mutable reference to the configured parameters
65    pub fn config_parameters_mut(&mut self) -> &mut ConfigParameters {
66        &mut self.config_parameters
67    }
68
69    /// Get the shared logger
70    pub fn logger(&self) -> &Logger {
71        &self.logger
72    }
73}
74
75#[cfg(test)]
76mod tests {
77    use slog::o;
78    use std::collections::HashMap;
79
80    use crate::configuration::{ConfigError, ConfigSource};
81
82    use super::*;
83
84    #[test]
85    fn require_unstable_return_ok_if_unstable_enabled() {
86        let unstable_enabled = true;
87        let context = CommandContext::new(
88            ConfigParameters::default(),
89            unstable_enabled,
90            true,
91            Logger::root(slog::Discard, o!()),
92        );
93
94        let result = context.require_unstable("test", None);
95        assert!(result.is_ok(), "Expected Ok, got {result:?}");
96    }
97
98    #[test]
99    fn require_unstable_return_err_if_unstable_disabled() {
100        let unstable_enabled = false;
101        let context = CommandContext::new(
102            ConfigParameters::default(),
103            unstable_enabled,
104            true,
105            Logger::root(slog::Discard, o!()),
106        );
107
108        let result = context.require_unstable("test", None);
109        assert!(result.is_err(), "Expected Err, got {result:?}");
110    }
111
112    #[test]
113    fn can_edit_config_parameters() {
114        struct ParamSource {
115            key: String,
116            value: String,
117        }
118        impl ConfigSource for ParamSource {
119            fn collect(&self) -> Result<HashMap<String, String>, ConfigError> {
120                Ok(HashMap::from([(self.key.clone(), self.value.clone())]))
121            }
122        }
123
124        let mut context = CommandContext::new(
125            ConfigParameters::default(),
126            false,
127            true,
128            Logger::root(slog::Discard, o!()),
129        );
130
131        assert_eq!(context.config_parameters_mut().get("key"), None,);
132
133        context
134            .config_parameters_mut()
135            .add_source(&ParamSource {
136                key: "key".to_string(),
137                value: "value".to_string(),
138            })
139            .unwrap();
140
141        assert_eq!(
142            context.config_parameters_mut().get("key"),
143            Some("value".to_string())
144        );
145    }
146}