use anyhow::{anyhow, Result}; use tokio::try_join; use crate::{ config::ConfigOpts, consul_actor::ConsulActor, fw_actor::FirewallActor, igd_actor::IgdActor, }; pub struct Diplonat { consul: ConsulActor, firewall: Option, igd: Option, } impl Diplonat { pub async fn new() -> Result { let config = ConfigOpts::from_env()?; println!("{:#?}", config); let consul_actor = ConsulActor::new(config.consul); let firewall_actor = FirewallActor::new(config.firewall, &consul_actor.rx_open_ports).await?; let igd_actor = IgdActor::new(config.igd, &consul_actor.rx_open_ports).await?; if firewall_actor.is_none() && igd_actor.is_none() { return Err(anyhow!( "At least enable *one* module, otherwise it's boring!" )) } let ctx = Self { consul: consul_actor, firewall: firewall_actor, igd: igd_actor, }; return Ok(ctx) } pub async fn listen(&mut self) -> Result<()> { let firewall = &mut self.firewall; let igd = &mut self.igd; try_join!( self.consul.listen(), async { match firewall { Some(x) => x.listen().await, None => Ok(()), } }, async { match igd { Some(x) => x.listen().await, None => Ok(()), } }, )?; return Ok(()) } }