mod force_local;
mod force_node;
use atm0s_sdn_identity::{ConnId, NodeId};
pub use force_local::ForceLocalRouter;
pub use force_node::ForceNodeRouter;
#[cfg(any(test, feature = "mock"))]
use mockall::automock;
pub type ServiceMeta = u32;
#[derive(Clone, Debug, Eq, PartialEq)]
pub enum RouteRule {
Direct,
ToNode(NodeId),
ToService(ServiceMeta),
ToKey(NodeId),
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub enum RouteAction {
Reject,
Local,
Next(ConnId, NodeId),
}
impl RouteAction {
pub fn is_local(&self) -> bool {
matches!(self, RouteAction::Local)
}
pub fn is_reject(&self) -> bool {
matches!(self, RouteAction::Reject)
}
pub fn is_remote(&self) -> bool {
matches!(self, RouteAction::Next(_, _))
}
}
#[cfg_attr(any(test, feature = "mock"), automock)]
pub trait RouterTable: Send + Sync {
fn path_to_node(&self, dest: NodeId) -> RouteAction;
fn path_to_key(&self, key: NodeId) -> RouteAction;
fn path_to_service(&self, service_id: u8) -> RouteAction;
fn derive_action(&self, route: &RouteRule, service_id: u8) -> RouteAction {
match route {
RouteRule::Direct => RouteAction::Local,
RouteRule::ToNode(dest) => self.path_to_node(*dest),
RouteRule::ToKey(key) => self.path_to_key(*key),
RouteRule::ToService(_) => self.path_to_service(service_id),
}
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_is_local() {
let local = RouteAction::Local;
let remote = RouteAction::Next(ConnId::from_in(1, 1), 2);
let reject = RouteAction::Reject;
assert!(local.is_local());
assert!(!remote.is_local());
assert!(!reject.is_local());
}
#[test]
fn test_is_reject() {
let local = RouteAction::Local;
let remote = RouteAction::Next(ConnId::from_in(1, 1), 2);
let reject = RouteAction::Reject;
assert!(!local.is_reject());
assert!(!remote.is_reject());
assert!(reject.is_reject());
}
#[test]
fn test_is_remote() {
let local = RouteAction::Local;
let remote = RouteAction::Next(ConnId::from_in(1, 1), 2);
let reject = RouteAction::Reject;
assert!(!local.is_remote());
assert!(remote.is_remote());
assert!(!reject.is_remote());
}
#[test]
fn test_derive_action_to_service() {
let router = ForceLocalRouter();
let route = RouteRule::ToService(3);
let service_id = 1;
assert_eq!(router.derive_action(&route, service_id), RouteAction::Local);
}
}