ceylon_runtime/config/
mesh_config.rs1use super::{AgentConfig, MemoryConfig};
4use crate::core::error::{Error, Result};
5use serde::{Deserialize, Serialize};
6use std::path::Path;
7
8#[derive(Debug, Clone, Serialize, Deserialize)]
34pub struct MeshConfig {
35 pub name: String,
37
38 #[serde(default)]
40 pub memory: Option<MemoryConfig>,
41
42 #[serde(default)]
44 pub agents: Vec<AgentConfig>,
45}
46
47impl Default for MeshConfig {
48 fn default() -> Self {
49 Self {
50 name: "mesh".to_string(),
51 memory: None,
52 agents: Vec::new(),
53 }
54 }
55}
56
57impl MeshConfig {
58 pub fn new(name: impl Into<String>) -> Self {
60 Self {
61 name: name.into(),
62 memory: None,
63 agents: Vec::new(),
64 }
65 }
66
67 pub fn from_toml(toml_str: &str) -> Result<Self> {
87 toml::from_str(toml_str)
88 .map_err(|e| Error::ConfigError(format!("Failed to parse TOML: {}", e)))
89 }
90
91 pub fn from_file(path: impl AsRef<Path>) -> Result<Self> {
101 let content = std::fs::read_to_string(path.as_ref()).map_err(|e| {
102 Error::ConfigError(format!(
103 "Failed to read file '{}': {}",
104 path.as_ref().display(),
105 e
106 ))
107 })?;
108 Self::from_toml(&content)
109 }
110
111 pub fn add_agent(mut self, agent: AgentConfig) -> Self {
113 self.agents.push(agent);
114 self
115 }
116
117 pub fn get_agent(&self, name: &str) -> Option<&AgentConfig> {
119 self.agents.iter().find(|a| a.name == name)
120 }
121}
122
123#[cfg(test)]
124mod tests {
125 use super::*;
126
127 #[test]
128 fn test_parse_mesh_config() {
129 let toml = r#"
130 name = "test_mesh"
131
132 [[agents]]
133 name = "agent1"
134 model = "ollama::llama2"
135 system_prompt = "First agent"
136
137 [[agents]]
138 name = "agent2"
139 model = "openai::gpt-4"
140 temperature = 0.8
141 "#;
142
143 let config = MeshConfig::from_toml(toml).unwrap();
144 assert_eq!(config.name, "test_mesh");
145 assert_eq!(config.agents.len(), 2);
146 assert_eq!(config.agents[0].name, "agent1");
147 assert_eq!(config.agents[1].name, "agent2");
148 assert_eq!(config.agents[1].temperature, Some(0.8));
149 }
150
151 #[test]
152 fn test_get_agent() {
153 let config = MeshConfig::new("test")
154 .add_agent(AgentConfig::new("agent1", "ollama::llama2"))
155 .add_agent(AgentConfig::new("agent2", "ollama::llama2"));
156
157 assert!(config.get_agent("agent1").is_some());
158 assert!(config.get_agent("agent2").is_some());
159 assert!(config.get_agent("nonexistent").is_none());
160 }
161
162 #[test]
163 fn test_empty_agents() {
164 let toml = r#"
165 name = "empty_mesh"
166 "#;
167
168 let config = MeshConfig::from_toml(toml).unwrap();
169 assert_eq!(config.name, "empty_mesh");
170 assert!(config.agents.is_empty());
171 }
172}