lark_webhook_notify/
config.rs1use figment::{
3 Figment,
4 providers::{Env, Format, Serialized, Toml},
5};
6use serde::{Deserialize, Serialize};
7
8use crate::error::{LarkWebhookError, Result};
9
10#[derive(Deserialize, Serialize, Debug, Clone, Default)]
20pub struct LarkWebhookSettings {
21 pub webhook_url: Option<String>,
23 pub webhook_secret: Option<String>,
25}
26
27impl LarkWebhookSettings {
28 pub fn load(
34 toml_file: Option<&str>,
35 webhook_url: Option<String>,
36 webhook_secret: Option<String>,
37 ) -> Result<Self> {
38 let path = toml_file.unwrap_or("lark_webhook.toml");
39 let mut settings: LarkWebhookSettings =
40 Figment::from(Serialized::defaults(LarkWebhookSettings::default()))
41 .merge(Toml::file(path))
42 .merge(Env::prefixed("LARK_"))
43 .extract()
44 .map_err(|e| LarkWebhookError::Config(e.to_string()))?;
45
46 if let Some(url) = webhook_url {
47 settings.webhook_url = Some(url);
48 }
49 if let Some(secret) = webhook_secret {
50 settings.webhook_secret = Some(secret);
51 }
52 Ok(settings)
53 }
54}
55
56#[cfg(test)]
57mod tests {
58 use super::*;
59 use std::sync::Mutex;
60
61 static ENV_MUTEX: Mutex<()> = Mutex::new(());
63
64 #[test]
65 fn test_defaults_are_none() {
66 let _guard = ENV_MUTEX.lock().unwrap();
67 let s = LarkWebhookSettings::load(Some("nonexistent_xyz.toml"), None, None).unwrap();
70 assert!(s.webhook_url.is_none());
71 assert!(s.webhook_secret.is_none());
72 }
73
74 #[test]
75 fn test_direct_params_override() {
76 let _guard = ENV_MUTEX.lock().unwrap();
77 let s = LarkWebhookSettings::load(
78 None,
79 Some("https://direct.url".to_owned()),
80 Some("direct_secret".to_owned()),
81 )
82 .unwrap();
83 assert_eq!(s.webhook_url.as_deref(), Some("https://direct.url"));
84 assert_eq!(s.webhook_secret.as_deref(), Some("direct_secret"));
85 }
86
87 #[test]
88 fn test_toml_file_loading() {
89 let _guard = ENV_MUTEX.lock().unwrap();
90 use std::io::Write;
91 let mut f = tempfile::NamedTempFile::new().unwrap();
92 write!(
93 f,
94 "webhook_url = \"https://toml.url\"\nwebhook_secret = \"toml_secret\"\n"
95 )
96 .unwrap();
97 let path = f.path().to_str().unwrap().to_owned();
98 let s = LarkWebhookSettings::load(Some(&path), None, None).unwrap();
99 assert_eq!(s.webhook_url.as_deref(), Some("https://toml.url"));
100 assert_eq!(s.webhook_secret.as_deref(), Some("toml_secret"));
101 }
102
103 #[test]
104 fn test_env_var_loading() {
105 let _guard = ENV_MUTEX.lock().unwrap();
106 unsafe {
110 std::env::set_var("LARK_WEBHOOK_URL", "https://env.url");
111 std::env::set_var("LARK_WEBHOOK_SECRET", "env_secret");
112 }
113 let result = LarkWebhookSettings::load(Some("nonexistent_xyz.toml"), None, None);
114 unsafe {
115 std::env::remove_var("LARK_WEBHOOK_URL");
116 std::env::remove_var("LARK_WEBHOOK_SECRET");
117 }
118 let s = result.unwrap();
119 assert_eq!(s.webhook_url.as_deref(), Some("https://env.url"));
120 assert_eq!(s.webhook_secret.as_deref(), Some("env_secret"));
121 }
122}