crates_docs/server/mod.rs
1//! 服务器模块
2//!
3//! 提供 MCP 服务器实现,支持多种传输协议(stdio、HTTP、SSE、Hybrid)。
4//!
5//! # 主要组件
6//!
7//! - `CratesDocsServer`: 主服务器结构体
8//! - `handler`: MCP 请求处理
9//! - `transport`: 传输层实现
10//! - `auth`: OAuth 认证支持
11//!
12//! # 示例
13//!
14//! ```rust,no_run
15//! use crates_docs::{AppConfig, CratesDocsServer};
16//!
17//! #[tokio::main]
18//! async fn main() -> Result<(), Box<dyn std::error::Error>> {
19//! let config = AppConfig::default();
20//! let server = CratesDocsServer::new(config)?;
21//!
22//! // 运行 HTTP 服务器
23//! server.run_http().await?;
24//!
25//! Ok(())
26//! }
27//! ```
28
29pub mod auth;
30pub mod handler;
31pub mod transport;
32
33use crate::cache::Cache;
34use crate::config::AppConfig;
35use crate::error::Result;
36use crate::tools::ToolRegistry;
37use rust_mcp_sdk::schema::{
38 Implementation, InitializeResult, ProtocolVersion, ServerCapabilities, ServerCapabilitiesTools,
39};
40use std::sync::Arc;
41
42/// 从配置模块重新导出 `ServerConfig` 以保持向后兼容
43pub use crate::config::ServerConfig;
44
45/// 从 handler 模块重新导出 `CratesDocsHandler`
46pub use handler::CratesDocsHandler;
47
48/// Crates Docs MCP 服务器
49///
50/// 主服务器结构体,管理配置、工具注册表和缓存。
51/// 支持多种传输协议:stdio、HTTP、SSE、Hybrid。
52///
53/// # 字段
54///
55/// - `config`: 应用配置
56/// - `tool_registry`: 工具注册表
57/// - `cache`: 缓存实例
58#[derive(Clone)]
59pub struct CratesDocsServer {
60 config: AppConfig,
61 tool_registry: Arc<ToolRegistry>,
62 cache: Arc<dyn Cache>,
63}
64
65impl CratesDocsServer {
66 /// 从组件创建服务器(内部初始化逻辑)
67 ///
68 /// # 参数
69 ///
70 /// * `config` - 应用配置
71 /// * `cache` - 缓存实例
72 ///
73 /// # 错误
74 ///
75 /// 如果文档服务创建失败,返回错误
76 fn from_parts(config: AppConfig, cache: Arc<dyn Cache>) -> crate::error::Result<Self> {
77 // Create document service with cache configuration
78 let doc_service = Arc::new(crate::tools::docs::DocService::with_config(
79 cache.clone(),
80 &config.cache,
81 )?);
82
83 // Create tool registry
84 let tool_registry = Arc::new(crate::tools::create_default_registry(&doc_service));
85
86 Ok(Self {
87 config,
88 tool_registry,
89 cache,
90 })
91 }
92
93 /// 创建新的服务器实例(同步)
94 ///
95 /// # 参数
96 ///
97 /// * `config` - 应用配置
98 ///
99 /// # 错误
100 ///
101 /// 如果缓存创建失败,返回错误
102 ///
103 /// # 注意
104 ///
105 /// 此方法仅支持内存缓存。如需使用 Redis,请使用 [`new_async`](Self::new_async) 方法。
106 ///
107 /// # 示例
108 ///
109 /// ```rust,no_run
110 /// use crates_docs::{AppConfig, CratesDocsServer};
111 ///
112 /// let config = AppConfig::default();
113 /// let server = CratesDocsServer::new(config).expect("Failed to create server");
114 /// ```
115 pub fn new(config: AppConfig) -> Result<Self> {
116 let cache_box: Box<dyn Cache> = crate::cache::create_cache(&config.cache)?;
117 let cache: Arc<dyn Cache> = Arc::from(cache_box);
118 Self::from_parts(config, cache)
119 }
120
121 /// 创建新的服务器实例(异步)
122 ///
123 /// # 参数
124 ///
125 /// * `config` - 应用配置
126 ///
127 /// # 错误
128 ///
129 /// 如果缓存创建失败,返回错误
130 ///
131 /// # 注意
132 ///
133 /// 支持内存缓存和 Redis 缓存(需要启用 `cache-redis` feature)。
134 ///
135 /// # 示例
136 ///
137 /// ```rust,no_run
138 /// use crates_docs::{AppConfig, CratesDocsServer};
139 ///
140 /// #[tokio::main]
141 /// async fn main() -> Result<(), Box<dyn std::error::Error>> {
142 /// let config = AppConfig::default();
143 /// let server = CratesDocsServer::new_async(config).await?;
144 /// Ok(())
145 /// }
146 /// ```
147 #[allow(unused_variables)]
148 #[allow(clippy::unused_async)]
149 pub async fn new_async(config: AppConfig) -> Result<Self> {
150 // Decide which creation method to use based on cache type and feature
151 #[cfg(feature = "cache-redis")]
152 {
153 let cache_box: Box<dyn Cache> = crate::cache::create_cache_async(&config.cache).await?;
154 let cache: Arc<dyn Cache> = Arc::from(cache_box);
155 Self::from_parts(config, cache)
156 }
157
158 #[cfg(not(feature = "cache-redis"))]
159 {
160 // No cache-redis feature, fall back to synchronous creation
161 let cache_box: Box<dyn Cache> = crate::cache::create_cache(&config.cache)?;
162 let cache: Arc<dyn Cache> = Arc::from(cache_box);
163 Self::from_parts(config, cache)
164 }
165 }
166
167 /// 获取服务器配置
168 #[must_use]
169 pub fn config(&self) -> &AppConfig {
170 &self.config
171 }
172
173 /// 获取工具注册表
174 #[must_use]
175 pub fn tool_registry(&self) -> &Arc<ToolRegistry> {
176 &self.tool_registry
177 }
178
179 /// 获取缓存实例
180 #[must_use]
181 pub fn cache(&self) -> &Arc<dyn Cache> {
182 &self.cache
183 }
184
185 /// 获取服务器信息
186 ///
187 /// 返回 MCP 初始化结果,包含服务器元数据和能力信息
188 #[must_use]
189 pub fn server_info(&self) -> InitializeResult {
190 InitializeResult {
191 server_info: Implementation {
192 name: self.config.server.name.clone(),
193 version: self.config.server.version.clone(),
194 title: Some("Crates Docs MCP Server".to_string()),
195 description: self.config.server.description.clone(),
196 icons: self.config.server.icons.clone(),
197 website_url: self.config.server.website_url.clone(),
198 },
199 capabilities: ServerCapabilities {
200 tools: Some(ServerCapabilitiesTools { list_changed: None }),
201 resources: None,
202 prompts: None,
203 experimental: None,
204 completions: None,
205 logging: None,
206 tasks: None,
207 },
208 protocol_version: ProtocolVersion::V2025_11_25.into(),
209 instructions: Some(
210 "Use this server to query Rust crate documentation. Supports crate lookup, crate search, and health check."
211 .to_string(),
212 ),
213 meta: None,
214 }
215 }
216
217 /// 运行 Stdio 服务器
218 ///
219 /// # 错误
220 ///
221 /// 如果服务器启动失败,返回错误
222 pub async fn run_stdio(&self) -> Result<()> {
223 transport::run_stdio_server(self).await
224 }
225
226 /// 运行 HTTP 服务器
227 ///
228 /// # 错误
229 ///
230 /// 如果服务器启动失败,返回错误
231 pub async fn run_http(&self) -> Result<()> {
232 transport::run_http_server(self).await
233 }
234
235 /// 运行 SSE 服务器
236 ///
237 /// # 错误
238 ///
239 /// 如果服务器启动失败,返回错误
240 pub async fn run_sse(&self) -> Result<()> {
241 transport::run_sse_server(self).await
242 }
243}