robotrt-middleware-core 0.1.0-beta.2

RobotRT modular robotics runtime and middleware components.
Documentation
use transport_core::{Endpoint, EndpointScheme};

use super::super::SimpleDiscovery;

impl SimpleDiscovery {
    pub(super) fn load_static_lines<'a, I>(&mut self, lines: I) -> Result<usize, String>
    where
        I: IntoIterator<Item = &'a str>,
    {
        let mut loaded = 0usize;

        for (index, raw) in lines.into_iter().enumerate() {
            let line = raw.trim();
            if line.is_empty() || line.starts_with('#') {
                continue;
            }

            let parts: Vec<&str> = line.split_whitespace().collect();
            if parts.is_empty() {
                continue;
            }

            match parts[0] {
                "topic" => {
                    if parts.len() < 2 {
                        return Err(format!("invalid topic directive at line {}", index + 1));
                    }
                    self.register_topic(parts[1]);
                    if parts.len() >= 3 {
                        self.add_labels(parts[1], parse_labels(parts[2]));
                    }
                    loaded += 1;
                }
                "service" => {
                    if parts.len() < 2 {
                        return Err(format!("invalid service directive at line {}", index + 1));
                    }
                    self.register_service(parts[1]);
                    if parts.len() >= 3 {
                        self.add_labels(parts[1], parse_labels(parts[2]));
                    }
                    loaded += 1;
                }
                "mission" => {
                    if parts.len() < 2 {
                        return Err(format!("invalid mission directive at line {}", index + 1));
                    }
                    self.register_mission(parts[1]);
                    if parts.len() >= 3 {
                        self.add_labels(parts[1], parse_labels(parts[2]));
                    }
                    loaded += 1;
                }
                "endpoint" => {
                    if parts.len() < 3 {
                        return Err(format!("invalid endpoint directive at line {}", index + 1));
                    }
                    let mut endpoint = parse_endpoint(parts[2])
                        .ok_or_else(|| format!("invalid endpoint address at line {}", index + 1))?;
                    if parts.len() >= 4 {
                        endpoint.labels = parse_labels(parts[3]);
                    }
                    self.register_endpoint(parts[1], endpoint);
                    loaded += 1;
                }
                unknown => {
                    return Err(format!(
                        "unknown directive '{unknown}' at line {}",
                        index + 1
                    ));
                }
            }
        }

        Ok(loaded)
    }
}

fn parse_labels(raw: &str) -> Vec<String> {
    raw.split(',')
        .map(str::trim)
        .filter(|s| !s.is_empty())
        .map(ToOwned::to_owned)
        .collect()
}

fn parse_endpoint(address: &str) -> Option<Endpoint> {
    let scheme = if address.starts_with("udp://") {
        EndpointScheme::Udp
    } else if address.starts_with("tcp://") {
        EndpointScheme::Tcp
    } else if address.starts_with("quic://") {
        EndpointScheme::Quic
    } else if address.starts_with("ipc://") {
        EndpointScheme::Ipc
    } else if address.starts_with("shm://") {
        EndpointScheme::SharedMemory
    } else {
        return None;
    };
    Some(Endpoint::new(scheme, address))
}