mecha10_cli/services/discovery/
mod.rs1#![allow(dead_code)]
2
3mod node_manager;
9mod parser;
10mod redis_ops;
11
12use anyhow::Result;
13use std::collections::HashMap;
14use std::time::{Duration, SystemTime};
15
16#[derive(Debug, Clone)]
18pub struct NodeInfo {
19 pub node_id: String,
20 pub node_type: String,
21 pub host: String,
22 pub port: u16,
23 pub last_seen: SystemTime,
24 pub metadata: HashMap<String, String>,
25}
26
27#[derive(Debug, Clone)]
29pub struct DiscoveryConfig {
30 pub redis_url: String,
31 pub discovery_topic: String,
32 pub heartbeat_interval: Duration,
33 pub node_timeout: Duration,
34 pub scan_subnet: Option<String>,
35}
36
37impl Default for DiscoveryConfig {
38 fn default() -> Self {
39 Self {
40 redis_url: "redis://localhost:6379".to_string(),
41 discovery_topic: "mecha10/discovery".to_string(),
42 heartbeat_interval: Duration::from_secs(5),
43 node_timeout: Duration::from_secs(30),
44 scan_subnet: None,
45 }
46 }
47}
48
49pub struct DiscoveryService {
76 discovered_nodes: HashMap<String, NodeInfo>,
77}
78
79impl DiscoveryService {
80 pub fn new() -> Self {
82 Self {
83 discovered_nodes: HashMap::new(),
84 }
85 }
86
87 pub async fn discover(&mut self, config: &DiscoveryConfig) -> Result<Vec<NodeInfo>> {
93 redis_ops::discover(config, &mut self.discovered_nodes).await
94 }
95
96 pub async fn monitor<F>(&mut self, config: &DiscoveryConfig, callback: F) -> Result<()>
103 where
104 F: FnMut(&NodeInfo),
105 {
106 redis_ops::monitor(config, &mut self.discovered_nodes, callback).await
107 }
108
109 pub fn get_nodes(&self) -> Vec<&NodeInfo> {
111 node_manager::get_nodes(&self.discovered_nodes)
112 }
113
114 pub fn get_node(&self, node_id: &str) -> Option<&NodeInfo> {
120 node_manager::get_node(&self.discovered_nodes, node_id)
121 }
122
123 pub fn cleanup_stale_nodes(&mut self, timeout: Duration) -> usize {
129 node_manager::cleanup_stale_nodes(&mut self.discovered_nodes, timeout)
130 }
131
132 pub async fn announce(&self, config: &DiscoveryConfig, node_info: &NodeInfo) -> Result<()> {
139 redis_ops::announce(config, node_info).await
140 }
141
142 pub async fn heartbeat(&self, config: &DiscoveryConfig, node_id: &str) -> Result<()> {
149 redis_ops::heartbeat(config, node_id).await
150 }
151
152 pub fn node_count(&self) -> usize {
154 node_manager::node_count(&self.discovered_nodes)
155 }
156
157 pub fn get_nodes_by_type(&self, node_type: &str) -> Vec<&NodeInfo> {
163 node_manager::get_nodes_by_type(&self.discovered_nodes, node_type)
164 }
165
166 pub fn clear(&mut self) {
168 node_manager::clear(&mut self.discovered_nodes);
169 }
170}
171
172impl Default for DiscoveryService {
173 fn default() -> Self {
174 Self::new()
175 }
176}