free_launch/
config.rs

1use color_eyre::Result;
2use serde::{Deserialize, Serialize};
3use std::fs;
4use std::path::PathBuf;
5
6#[derive(Debug, Clone, Serialize, Deserialize)]
7pub struct Config {
8    pub version: String,
9    pub providers: Vec<SearchProvider>,
10}
11
12#[derive(Debug, Clone, Serialize, Deserialize)]
13pub struct SearchProvider {
14    pub name: String,
15    pub aliases: Vec<String>,
16    pub url: String,
17    pub browser: Option<String>,
18}
19
20impl Config {
21    /// Load config from the default search-cli config location
22    pub fn load() -> Result<Option<Self>> {
23        let config_path = Self::default_config_path();
24
25        if !config_path.exists() {
26            return Ok(None);
27        }
28
29        let content = fs::read_to_string(&config_path)?;
30        let config: Config = serde_yaml::from_str(&content)?;
31        Ok(Some(config))
32    }
33
34    /// Get the default config file path: ~/.config/search/config.yaml
35    fn default_config_path() -> PathBuf {
36        dirs::home_dir()
37            .unwrap_or_else(|| PathBuf::from("."))
38            .join(".config")
39            .join("search")
40            .join("config.yaml")
41    }
42}
43
44impl SearchProvider {
45    /// Check if the given query matches any of this provider's aliases
46    pub fn matches_alias(&self, query: &str) -> bool {
47        self.aliases.iter().any(|alias| query.starts_with(alias))
48    }
49
50    /// Get the matching alias from the query, if any
51    pub fn get_matching_alias(&self, query: &str) -> Option<&str> {
52        // Get the first word from the query
53        let first_word = query.split_whitespace().next()?;
54
55        // Find the longest matching alias that equals the first word
56        let mut best_match = "";
57        for alias in &self.aliases {
58            if first_word == alias && alias.len() > best_match.len() {
59                best_match = alias;
60            }
61        }
62
63        if best_match.is_empty() {
64            None
65        } else {
66            Some(best_match)
67        }
68    }
69}