1use crate::{Error, HandlerRegistry, Result};
2use pforge_config::ForgeConfig;
3use std::sync::Arc;
4use tokio::sync::RwLock;
5
6pub struct McpServer {
8 config: ForgeConfig,
9 registry: Arc<RwLock<HandlerRegistry>>,
10}
11
12impl McpServer {
13 pub fn new(config: ForgeConfig) -> Self {
15 Self {
16 config,
17 registry: Arc::new(RwLock::new(HandlerRegistry::new())),
18 }
19 }
20
21 pub async fn register_handlers(&self) -> Result<()> {
23 let mut registry = self.registry.write().await;
24
25 for tool in &self.config.tools {
26 match tool {
27 pforge_config::ToolDef::Native { name, .. } => {
28 eprintln!("Note: Native handler '{}' requires handler implementation", name);
30 }
31 pforge_config::ToolDef::Cli {
32 name,
33 command,
34 args,
35 cwd,
36 env,
37 stream,
38 ..
39 } => {
40 use crate::handlers::cli::CliHandler;
41 let handler = CliHandler::new(
42 command.clone(),
43 args.clone(),
44 cwd.clone(),
45 env.clone(),
46 None, *stream,
48 );
49 registry.register(name, handler);
50 eprintln!("Registered CLI handler: {}", name);
51 }
52 pforge_config::ToolDef::Http {
53 name,
54 endpoint,
55 method,
56 headers,
57 auth,
58 ..
59 } => {
60 use crate::handlers::http::{AuthConfig as HttpAuthConfig, HttpHandler, HttpMethod as HandlerHttpMethod};
61
62 let handler_method = match method {
63 pforge_config::HttpMethod::Get => HandlerHttpMethod::Get,
64 pforge_config::HttpMethod::Post => HandlerHttpMethod::Post,
65 pforge_config::HttpMethod::Put => HandlerHttpMethod::Put,
66 pforge_config::HttpMethod::Delete => HandlerHttpMethod::Delete,
67 pforge_config::HttpMethod::Patch => HandlerHttpMethod::Patch,
68 };
69
70 let handler_auth = auth.as_ref().map(|a| match a {
71 pforge_config::AuthConfig::Bearer { token } => {
72 HttpAuthConfig::Bearer {
73 token: token.clone(),
74 }
75 }
76 pforge_config::AuthConfig::Basic { username, password } => {
77 HttpAuthConfig::Basic {
78 username: username.clone(),
79 password: password.clone(),
80 }
81 }
82 pforge_config::AuthConfig::ApiKey { key, header } => {
83 HttpAuthConfig::ApiKey {
84 key: key.clone(),
85 header: header.clone(),
86 }
87 }
88 });
89
90 let handler = HttpHandler::new(
91 endpoint.clone(),
92 handler_method,
93 headers.clone(),
94 handler_auth,
95 );
96 registry.register(name, handler);
97 eprintln!("Registered HTTP handler: {}", name);
98 }
99 pforge_config::ToolDef::Pipeline { name, .. } => {
100 eprintln!("Note: Pipeline handler '{}' pending implementation", name);
101 }
102 }
103 }
104
105 Ok(())
106 }
107
108 pub async fn run(&self) -> Result<()> {
110 eprintln!("Starting MCP server: {} v{}", self.config.forge.name, self.config.forge.version);
111 eprintln!("Transport: {:?}", self.config.forge.transport);
112 eprintln!("Tools registered: {}", self.config.tools.len());
113
114 self.register_handlers().await?;
116
117 eprintln!("\n⚠ MCP protocol loop not yet implemented");
120 eprintln!("Server configuration loaded and handlers registered successfully");
121 eprintln!("Press Ctrl+C to exit");
122
123 tokio::signal::ctrl_c().await.map_err(|e| Error::Io(e))?;
125
126 eprintln!("\nShutting down...");
127 Ok(())
128 }
129
130 pub fn registry(&self) -> Arc<RwLock<HandlerRegistry>> {
132 self.registry.clone()
133 }
134}