use super::{channel::Channel, envelope::Envelope};
use std::collections::HashMap;

pub struct EnvelopeBroker {
    channels: HashMap<String, Channel>,
}

impl EnvelopeBroker {
    pub fn new() -> Self {
        Self {
            channels: HashMap::new(),
        }
    }

    pub fn send(&mut self, env: Envelope) {
        self.channels
            .entry(env.channel.clone())
            .or_insert_with(|| Channel::new(&env.channel))
            .push(env);
    }

    pub fn receive(&mut self, channel: &str) -> Option<Envelope> {
        self.channels.get_mut(channel)?.pop()
    }

    pub fn drain(&mut self, channel: &str) -> Vec<Envelope> {
        let ch = self.channels.get_mut(channel);
        match ch {
            None => Vec::new(),
            Some(c) => std::iter::from_fn(|| c.pop()).collect(),
        }
    }
}

impl Default for EnvelopeBroker {
    fn default() -> Self {
        Self::new()
    }
}
