1use std::collections::HashMap;
5use std::num::NonZeroUsize;
6
7use crate::tools::ToolsConfig;
8use serde::{Deserialize, Serialize};
9use zeph_common::secret::Secret;
10
11use crate::agent::{AgentConfig, FocusConfig, GoalConfig, SubAgentConfig};
12use crate::channels::{
13 A2aClientConfig, A2aServerConfig, DiscordConfig, McpConfig, SlackConfig, TelegramConfig,
14};
15use crate::classifiers::ClassifiersConfig;
16use crate::cli::CliConfig;
17use crate::cocoon::CocoonConfig;
18use crate::defaults::{default_skill_paths, default_sqlite_path_field};
19use crate::execution::ExecutionConfig;
20use crate::experiment::{ExperimentConfig, OrchestrationConfig};
21use crate::features::{
22 CostConfig, DaemonConfig, DebugConfig, GatewayConfig, IndexConfig, RegistryConfig,
23 SchedulerConfig, SkillPromptMode, SkillsConfig, VaultConfig,
24};
25use crate::hooks::HooksConfig;
26use crate::learning::LearningConfig;
27use crate::logging::LoggingConfig;
28use crate::memory::{
29 CompressionConfig, DocumentConfig, GraphConfig, MagicDocsConfig, MemoryConfig, SemanticConfig,
30 SessionsConfig, SidequestConfig, TierConfig, VectorBackend,
31};
32use crate::metrics::MetricsConfig;
33use crate::notifications::NotificationsConfig;
34use crate::providers::{
35 LlmConfig, ProviderEntry, get_default_embedding_model, get_default_response_cache_ttl_secs,
36 get_default_router_ema_alpha, get_default_router_reorder_interval,
37};
38use crate::security::TrustConfig;
39use crate::security::{SecurityConfig, TimeoutConfig};
40use crate::telemetry::TelemetryConfig;
41use crate::ui::LspConfig;
42use crate::ui::{AcpConfig, TuiConfig};
43
44#[derive(Debug, Deserialize, Serialize)]
50pub struct Config {
51 pub agent: AgentConfig,
52 pub llm: LlmConfig,
53 pub skills: SkillsConfig,
54 pub memory: MemoryConfig,
55 #[serde(skip_serializing_if = "Option::is_none")]
56 pub telegram: Option<TelegramConfig>,
57 #[serde(skip_serializing_if = "Option::is_none")]
58 pub discord: Option<DiscordConfig>,
59 #[serde(skip_serializing_if = "Option::is_none")]
60 pub slack: Option<SlackConfig>,
61 #[serde(default)]
62 pub tools: ToolsConfig,
63 #[serde(default)]
67 pub execution: ExecutionConfig,
68 #[serde(default)]
69 pub a2a: A2aServerConfig,
70 #[serde(default)]
73 pub a2a_client: A2aClientConfig,
74 #[serde(default)]
75 pub mcp: McpConfig,
76 #[serde(default)]
77 pub index: IndexConfig,
78 #[serde(default)]
79 pub vault: VaultConfig,
80 #[serde(default)]
81 pub security: SecurityConfig,
82 #[serde(default)]
83 pub timeouts: TimeoutConfig,
84 #[serde(default)]
85 pub cost: CostConfig,
86 #[serde(default)]
87 pub gateway: GatewayConfig,
88 #[serde(default)]
89 pub daemon: DaemonConfig,
90 #[serde(default)]
91 pub scheduler: SchedulerConfig,
92 #[serde(default)]
93 pub tui: TuiConfig,
94 #[serde(default)]
95 pub acp: AcpConfig,
96 #[serde(default)]
97 pub agents: SubAgentConfig,
98 #[serde(default)]
99 pub orchestration: OrchestrationConfig,
100 #[serde(default)]
101 pub classifiers: ClassifiersConfig,
102 #[serde(default)]
103 pub experiments: ExperimentConfig,
104 #[serde(default)]
105 pub debug: DebugConfig,
106 #[serde(default)]
107 pub logging: LoggingConfig,
108 #[serde(default)]
109 pub hooks: HooksConfig,
110 #[serde(default)]
111 pub lsp: LspConfig,
112 #[serde(default)]
114 pub magic_docs: MagicDocsConfig,
115 #[serde(default)]
117 pub telemetry: TelemetryConfig,
118 #[serde(default)]
120 pub metrics: MetricsConfig,
121 #[serde(default)]
123 pub session: crate::session::SessionConfig,
124 #[serde(default)]
126 pub serve: crate::serve::ServeConfig,
127 #[serde(default)]
129 pub cli: CliConfig,
130 #[serde(default)]
132 pub quality: crate::quality::QualityConfig,
133 #[serde(default)]
135 pub notifications: NotificationsConfig,
136 #[serde(default)]
138 pub goals: GoalConfig,
139 #[serde(default)]
141 pub cocoon: CocoonConfig,
142 #[serde(skip)]
144 pub secrets: ResolvedSecrets,
145 #[serde(default)]
147 pub worktree: crate::worktree::WorktreeConfig,
148 #[serde(default)]
150 pub durable: crate::durable::DurableConfig,
151 #[serde(default)]
153 pub integrity: crate::integrity::IntegrityConfig,
154 #[serde(default)]
158 pub caveman: crate::features::CavemanConfig,
159 #[serde(default)]
164 pub knowledge: crate::knowledge::KnowledgeConfig,
165 #[serde(default)]
168 pub plugins: crate::plugins::PluginsConfig,
169 #[cfg(feature = "deep-link")]
171 #[serde(default)]
172 pub deep_link: crate::deep_link::DeepLinkConfig,
173}
174
175#[derive(Debug, Default)]
180pub struct ResolvedSecrets {
181 pub claude_api_key: Option<Secret>,
182 pub openai_api_key: Option<Secret>,
183 pub gemini_api_key: Option<Secret>,
184 pub compatible_api_keys: HashMap<String, Secret>,
185 pub discord_token: Option<Secret>,
186 pub slack_bot_token: Option<Secret>,
187 pub slack_signing_secret: Option<Secret>,
188 pub gonka_private_key: Option<Secret>,
190 pub gonka_address: Option<Secret>,
192 pub cocoon_access_hash: Option<Secret>,
194 pub skill_registry_token: Option<Secret>,
198 pub web_search_api_key: Option<Secret>,
202 pub custom: HashMap<String, Secret>,
209}
210
211impl Default for Config {
212 #[allow(clippy::too_many_lines)] fn default() -> Self {
214 Self {
215 agent: AgentConfig {
216 name: "Zeph".into(),
217 max_tool_iterations: 10,
218 auto_update_check: true,
219 instruction_files: Vec::new(),
220 instruction_auto_detect: true,
221 max_tool_retries: 2,
222 tool_repeat_threshold: 2,
223 max_retry_duration_secs: 30,
224 focus: FocusConfig::default(),
225 tool_filter: crate::agent::ToolFilterConfig::default(),
226 budget_hint_enabled: true,
227 supervisor: crate::agent::TaskSupervisorConfig::default(),
228 time_reminder_enabled: false,
229 time_reminder_interval_requests: 10,
230 },
231 llm: LlmConfig {
232 providers: vec![ProviderEntry::default()],
238 routing: crate::providers::LlmRoutingStrategy::None,
239 embedding_model: get_default_embedding_model(),
240 candle: None,
241 stt: None,
242 response_cache_enabled: false,
243 response_cache_ttl_secs: get_default_response_cache_ttl_secs(),
244 semantic_cache_enabled: false,
245 semantic_cache_threshold: 0.95,
246 semantic_cache_max_candidates: 10,
247 router_ema_enabled: false,
248 router_ema_alpha: get_default_router_ema_alpha(),
249 router_reorder_interval: get_default_router_reorder_interval(),
250 router: None,
251 instruction_file: None,
252 summary_model: None,
253 summary_provider: None,
254 complexity_routing: None,
255 coe: None,
256 stream_limits: crate::StreamLimits::default(),
257 },
258 skills: SkillsConfig {
259 paths: default_skill_paths(),
260 max_active_skills: NonZeroUsize::new(5).expect("5 is non-zero"),
261 disambiguation_threshold: 0.20,
262 min_injection_score: 0.20,
263 cosine_weight: 0.7,
264 hybrid_search: true,
265 bm25_alpha: 0.7,
266 learning: LearningConfig::default(),
267 trust: TrustConfig::default(),
268 registry: RegistryConfig::default(),
269 prompt_mode: SkillPromptMode::Auto,
270 two_stage_matching: false,
271 confusability_threshold: 0.0,
272 rl_routing_enabled: false,
273 rl_learning_rate: 0.01,
274 rl_weight: 0.3,
275 rl_persist_interval: 10,
276 rl_warmup_updates: 50,
277 rl_embed_dim: None,
278 query_rewrite_provider: crate::providers::ProviderName::default(),
279 generation_provider: crate::providers::ProviderName::default(),
280 generation_timeout_ms: 60_000,
281 generation_output_dir: None,
282 mining: crate::features::SkillMiningConfig::default(),
283 evaluation: crate::features::SkillEvaluationConfig::default(),
284 proactive_exploration: crate::features::ProactiveExplorationConfig::default(),
285 disambiguate_provider: crate::providers::ProviderName::default(),
286 semantic_scan: false,
287 semantic_scan_provider: crate::providers::ProviderName::default(),
288 group_structured: false,
289 support_similarity_threshold: 0.50,
290 subagent_skill_token_budget: NonZeroUsize::new(12_000).expect("12000 is non-zero"),
291 },
292 memory: MemoryConfig {
293 sqlite_path: default_sqlite_path_field(),
294 history_limit: 50,
295 qdrant_url: "http://localhost:6334".into(),
296 qdrant_api_key: None,
297 qdrant_timeout_secs: 10,
298 semantic: SemanticConfig::default(),
299 summarization_threshold: 50,
300 summarization_llm_timeout_secs: 60,
301 context_budget_tokens: 0,
302 soft_compaction_threshold: 0.60,
303 hard_compaction_threshold: 0.90,
304 compaction_preserve_tail: 6,
305 compaction_cooldown_turns: 2,
306 auto_budget: true,
307 prune_protect_tokens: 40_000,
308 cross_session_score_threshold: 0.35,
309 vector_backend: VectorBackend::default(),
310 token_safety_margin: 1.0,
311 redact_credentials: true,
312 autosave_assistant: true,
313 autosave_min_length: 20,
314 tool_call_cutoff: 6,
315 sqlite_pool_size: 5,
316 sessions: SessionsConfig::default(),
317 documents: DocumentConfig::default(),
318 eviction: crate::memory::EvictionConfig::default(),
319 compression: CompressionConfig::default(),
320 sidequest: SidequestConfig::default(),
321 graph: GraphConfig::default(),
322 compression_guidelines: crate::memory::CompressionGuidelinesConfig::default(),
323 shutdown_summary: true,
324 shutdown_summary_min_messages: 4,
325 shutdown_summary_max_messages: 20,
326 shutdown_summary_timeout_secs: 30,
327 shutdown_summary_provider: crate::providers::ProviderName::default(),
328 compaction_provider: crate::providers::ProviderName::default(),
329 structured_summaries: false,
330 tiers: TierConfig::default(),
331 admission: crate::memory::AdmissionConfig::default(),
332 digest: crate::memory::DigestConfig::default(),
333 context_strategy: crate::memory::ContextStrategy::default(),
334 crossover_turn_threshold: 20,
335 consolidation: crate::memory::ConsolidationConfig::default(),
336 forgetting: crate::memory::ForgettingConfig::default(),
337 database_url: None,
338 store_routing: crate::memory::StoreRoutingConfig::default(),
339 persona: crate::memory::PersonaConfig::default(),
340 trajectory: crate::memory::TrajectoryConfig::default(),
341 category: crate::memory::CategoryConfig::default(),
342 tree: crate::memory::TreeConfig::default(),
343 microcompact: crate::memory::MicrocompactConfig::default(),
344 autodream: crate::memory::AutoDreamConfig::default(),
345 key_facts_dedup_threshold: 0.95,
346 compression_spectrum: crate::features::CompressionSpectrumConfig::default(),
347 retrieval: crate::memory::RetrievalConfig::default(),
348 reasoning: crate::memory::ReasoningConfig::default(),
349 hebbian: crate::memory::HebbianConfig::default(),
350 memcot: crate::memory::MemCotConfig::default(),
351 retrieval_failures: crate::memory::RetrievalFailuresConfig::default(),
352 quality_gate: crate::memory::WriteQualityGateConfig::default(),
353 tiered_retrieval: crate::memory::TieredRetrievalConfig::default(),
354 type_aware_compose: crate::memory::TypeAwareComposeConfig::default(),
355 optical_forgetting: crate::memory::OpticalForgettingConfig::default(),
356 em_graph: crate::memory::EmGraphConfig::default(),
357 episodic_consolidation: crate::memory::EpisodicConsolidationConfig::default(),
358 shadow_memory: crate::memory::TrajectoryRiskAccumulatorConfig::default(),
359 five_signal: crate::memory::FiveSignalConfig::default(),
360 fidelity: None,
361 store: crate::memory::CrossThreadStoreConfig::default(),
362 consent_gate: crate::memory::ConsentGateConfig::default(),
363 },
364 telegram: None,
365 discord: None,
366 slack: None,
367 tools: ToolsConfig::default(),
368 execution: ExecutionConfig::default(),
369 a2a: A2aServerConfig::default(),
370 a2a_client: A2aClientConfig::default(),
371 mcp: McpConfig::default(),
372 index: IndexConfig::default(),
373 vault: VaultConfig::default(),
374 security: SecurityConfig::default(),
375 timeouts: TimeoutConfig::default(),
376 cost: CostConfig::default(),
377 gateway: GatewayConfig::default(),
378 daemon: DaemonConfig::default(),
379 scheduler: SchedulerConfig::default(),
380 tui: TuiConfig::default(),
381 acp: AcpConfig::default(),
382 agents: SubAgentConfig::default(),
383 orchestration: OrchestrationConfig::default(),
384 classifiers: ClassifiersConfig::default(),
385 experiments: ExperimentConfig::default(),
386 debug: DebugConfig::default(),
387 logging: LoggingConfig::default(),
388 lsp: LspConfig::default(),
389 hooks: HooksConfig::default(),
390 magic_docs: MagicDocsConfig::default(),
391 telemetry: TelemetryConfig::default(),
392 metrics: MetricsConfig::default(),
393 session: crate::session::SessionConfig::default(),
394 serve: crate::serve::ServeConfig::default(),
395 cli: CliConfig::default(),
396 quality: crate::quality::QualityConfig::default(),
397 notifications: NotificationsConfig::default(),
398 goals: GoalConfig::default(),
399 cocoon: CocoonConfig::default(),
400 secrets: ResolvedSecrets::default(),
401 worktree: crate::worktree::WorktreeConfig::default(),
402 durable: crate::durable::DurableConfig::default(),
403 integrity: crate::integrity::IntegrityConfig::default(),
404 caveman: crate::features::CavemanConfig::default(),
405 knowledge: crate::knowledge::KnowledgeConfig::default(),
406 plugins: crate::plugins::PluginsConfig::default(),
407 #[cfg(feature = "deep-link")]
408 deep_link: crate::deep_link::DeepLinkConfig::default(),
409 }
410 }
411}