use crate::config::ListenerConfig;
use std::collections::HashMap;
pub type ListenerKey = String;
pub fn listener_key(cfg: &ListenerConfig) -> ListenerKey {
cfg.bind.to_url()
}
#[derive(Debug)]
pub struct ListenerDiff<'a> {
pub added: Vec<&'a ListenerConfig>,
pub removed: Vec<&'a ListenerConfig>,
#[cfg_attr(not(test), allow(dead_code))]
pub unchanged: Vec<(&'a ListenerConfig, &'a ListenerConfig)>,
}
pub fn diff_listeners<'a>(
old: &'a [ListenerConfig],
new: &'a [ListenerConfig],
) -> ListenerDiff<'a> {
let old_by_key: HashMap<ListenerKey, &ListenerConfig> =
old.iter().map(|c| (listener_key(c), c)).collect();
let new_by_key: HashMap<ListenerKey, &ListenerConfig> =
new.iter().map(|c| (listener_key(c), c)).collect();
let mut added = Vec::new();
let mut removed = Vec::new();
let mut unchanged = Vec::new();
for (key, new_cfg) in &new_by_key {
match old_by_key.get(key) {
Some(old_cfg) => unchanged.push((*old_cfg, *new_cfg)),
None => added.push(*new_cfg),
}
}
for (key, old_cfg) in &old_by_key {
if !new_by_key.contains_key(key) {
removed.push(*old_cfg);
}
}
added.sort_by_key(|c| listener_key(c));
removed.sort_by_key(|c| listener_key(c));
unchanged.sort_by_key(|(o, _)| listener_key(o));
ListenerDiff { added, removed, unchanged }
}