Skip to main content

llm_manager/config/
presets.rs

1use std::collections::HashMap;
2use std::path::PathBuf;
3
4use serde::{Deserialize, Serialize};
5
6use crate::config::config_base_dir;
7use crate::config::SystemPromptPreset;
8use crate::config::builtin_system_prompt_presets;
9use crate::config::store::{load_all_from_dir, move_to_unused, save_yaml};
10
11/// Directory for per-preset YAML configs.
12pub fn presets_config_dir() -> PathBuf {
13    config_base_dir()
14        .join("llm-manager")
15        .join("presets")
16}
17
18/// Directory for unused (deleted) preset configs.
19pub fn unused_presets_dir() -> PathBuf {
20    config_base_dir()
21        .join("llm-manager")
22        .join("unused_presets")
23}
24
25/// System prompt preset store — manages per-preset YAML configs.
26#[derive(Debug, Clone, Serialize, Deserialize)]
27pub struct PresetStore {
28    presets_dir: PathBuf,
29    unused_dir: PathBuf,
30    cache: HashMap<String, SystemPromptPreset>,
31}
32
33impl PresetStore {
34    pub fn new() -> Self {
35        let presets_dir = presets_config_dir();
36        let unused_dir = unused_presets_dir();
37        let cache = load_all_from_dir(&presets_dir);
38        Self {
39            presets_dir,
40            unused_dir,
41            cache,
42        }
43    }
44
45   /// Get all user-defined presets (excluding built-ins).
46        pub fn user_presets(&self) -> Vec<SystemPromptPreset> {
47            let builtin = builtin_system_prompt_presets();
48            self.cache
49                .values()
50                .filter(|p| !builtin.iter().any(|b| b.name == p.name))
51                .cloned()
52                .collect()
53        }
54
55  /// Save (or update) a preset.
56        pub fn save(&mut self, preset: &SystemPromptPreset) {
57            save_yaml(&preset.name, preset, &self.presets_dir, &self.unused_dir);
58            self.cache.insert(preset.name.clone(), preset.clone());
59        }
60
61        /// Insert a built-in preset into the in-memory cache only (no disk I/O).
62        pub fn insert_builtin(&mut self, preset: SystemPromptPreset) {
63            self.cache.insert(preset.name.clone(), preset);
64        }
65
66    /// Delete a preset by moving it to the unused directory.
67    pub fn delete(&mut self, name: &str) -> bool {
68        let builtin = builtin_system_prompt_presets();
69        if builtin.iter().any(|b| b.name == name) {
70            return false;
71        }
72        move_to_unused(name, &self.presets_dir, &self.unused_dir);
73        self.cache.remove(name);
74        true
75    }
76
77    /// Get a preset by name.
78    pub fn get(&self, name: &str) -> Option<&SystemPromptPreset> {
79        self.cache.get(name)
80    }
81
82    /// Get all presets (built-in + user).
83    pub fn all(&self) -> Vec<SystemPromptPreset> {
84        let builtin = builtin_system_prompt_presets();
85        let mut all: Vec<SystemPromptPreset> = builtin.clone();
86        for p in self.cache.values() {
87            if !builtin.iter().any(|b| b.name == p.name) {
88                all.push(p.clone());
89            }
90        }
91        all
92    }
93}
94
95impl Default for PresetStore {
96    fn default() -> Self {
97        Self::new()
98    }
99}