pipedash_plugin_api/
config.rs1use std::collections::HashMap;
2
3use reqwest::Url;
4
5use crate::error::{
6 PluginError,
7 PluginResult,
8};
9use crate::http::parse_http_url;
10
11pub const PIPELINE_ID_SEPARATOR: &str = "__";
12
13pub fn value<'a>(config: &'a HashMap<String, String>, key: &str) -> Option<&'a str> {
14 config.get(key).map(|v| v.trim()).filter(|v| !v.is_empty())
15}
16
17pub fn required_value<'a>(
18 config: &'a HashMap<String, String>, key: &str, missing_message: &str,
19) -> PluginResult<&'a str> {
20 value(config, key).ok_or_else(|| PluginError::InvalidConfig(missing_message.to_string()))
21}
22
23pub fn credential(config: &HashMap<String, String>, key: &str) -> PluginResult<String> {
24 required_value(config, key, &format!("Missing {key} in config")).map(str::to_string)
25}
26
27pub fn comma_separated(value: &str) -> impl Iterator<Item = &str> + '_ {
28 value
29 .split(',')
30 .map(str::trim)
31 .filter(|item| !item.is_empty())
32}
33
34pub fn csv_list(config: &HashMap<String, String>, key: &str) -> Option<Vec<String>> {
35 config
36 .get(key)
37 .map(|items| comma_separated(items).map(str::to_string).collect())
38}
39
40pub fn selected_items(config: &HashMap<String, String>) -> Option<Vec<String>> {
41 csv_list(config, "selected_items")
42}
43
44pub fn bool_value(config: &HashMap<String, String>, key: &str) -> bool {
45 config
46 .get(key)
47 .and_then(|v| v.parse::<bool>().ok())
48 .unwrap_or(false)
49}
50
51pub fn insecure(config: &HashMap<String, String>) -> bool {
52 bool_value(config, "insecure")
53}
54
55pub fn base_url<'a>(config: &'a HashMap<String, String>, key: &str) -> Option<&'a str> {
56 value(config, key)
57 .map(|url| url.trim_end_matches('/'))
58 .filter(|url| !url.is_empty())
59}
60
61pub fn required_base_url<'a>(
62 config: &'a HashMap<String, String>, key: &str, missing_message: &str,
63) -> PluginResult<&'a str> {
64 base_url(config, key).ok_or_else(|| PluginError::InvalidConfig(missing_message.to_string()))
65}
66
67pub fn http_base_url<'a>(
68 config: &'a HashMap<String, String>, key: &str, missing_message: &str, label: &str,
69) -> PluginResult<(&'a str, Url)> {
70 let raw = required_base_url(config, key, missing_message)?;
71 let parsed = parse_http_url(raw, label)?;
72 if parsed.query().is_some() || parsed.fragment().is_some() {
73 return Err(PluginError::InvalidConfig(format!(
74 "Invalid {label} URL: remove the query or fragment"
75 )));
76 }
77 Ok((raw, parsed))
78}
79
80pub fn invalid_pipeline_id(id: &str) -> PluginError {
81 PluginError::InvalidConfig(format!("Invalid pipeline ID format: {id}"))
82}
83
84#[cfg(test)]
85mod tests;