agent_sdk/subagent/
factory.rs1use std::sync::Arc;
30
31use anyhow::{Context, Result};
32
33use crate::llm::LlmProvider;
34use crate::tools::ToolRegistry;
35
36use super::{SubagentConfig, SubagentTool};
37
38pub struct SubagentFactory<P>
43where
44 P: LlmProvider + 'static,
45{
46 provider: Arc<P>,
47 read_only_registry: Option<Arc<ToolRegistry<()>>>,
48 full_registry: Option<Arc<ToolRegistry<()>>>,
49}
50
51impl<P> SubagentFactory<P>
52where
53 P: LlmProvider + 'static,
54{
55 #[must_use]
57 pub const fn new(provider: Arc<P>) -> Self {
58 Self {
59 provider,
60 read_only_registry: None,
61 full_registry: None,
62 }
63 }
64
65 #[must_use]
69 pub fn with_read_only_registry(mut self, registry: ToolRegistry<()>) -> Self {
70 self.read_only_registry = Some(Arc::new(registry));
71 self
72 }
73
74 #[must_use]
76 pub fn with_full_registry(mut self, registry: ToolRegistry<()>) -> Self {
77 self.full_registry = Some(Arc::new(registry));
78 self
79 }
80
81 pub fn create_read_only(&self, config: SubagentConfig) -> Result<SubagentTool<P>> {
90 let registry = self
91 .read_only_registry
92 .as_ref()
93 .context("read-only registry not set; call with_read_only_registry first")?;
94 Ok(SubagentTool::new(
95 config,
96 Arc::clone(&self.provider),
97 Arc::clone(registry),
98 ))
99 }
100
101 pub fn create_full_access(&self, config: SubagentConfig) -> Result<SubagentTool<P>> {
107 let registry = self
108 .full_registry
109 .as_ref()
110 .context("full registry not set; call with_full_registry first")?;
111 Ok(SubagentTool::new(
112 config,
113 Arc::clone(&self.provider),
114 Arc::clone(registry),
115 ))
116 }
117
118 #[must_use]
120 pub fn create_with_registry(
121 &self,
122 config: SubagentConfig,
123 registry: Arc<ToolRegistry<()>>,
124 ) -> SubagentTool<P> {
125 SubagentTool::new(config, Arc::clone(&self.provider), registry)
126 }
127
128 #[must_use]
130 pub fn provider(&self) -> Arc<P> {
131 Arc::clone(&self.provider)
132 }
133}
134
135impl<P> Clone for SubagentFactory<P>
136where
137 P: LlmProvider + 'static,
138{
139 fn clone(&self) -> Self {
140 Self {
141 provider: Arc::clone(&self.provider),
142 read_only_registry: self.read_only_registry.clone(),
143 full_registry: self.full_registry.clone(),
144 }
145 }
146}
147
148#[cfg(test)]
149mod tests {
150 use super::*;
151
152 #[test]
153 fn test_subagent_config_builder() {
154 let config = SubagentConfig::new("test")
155 .with_system_prompt("You are a test agent")
156 .with_max_turns(5)
157 .with_timeout_ms(30000);
158
159 assert_eq!(config.name, "test");
160 assert_eq!(config.system_prompt, "You are a test agent");
161 assert_eq!(config.max_turns, Some(5));
162 assert_eq!(config.timeout_ms, Some(30000));
163 }
164}