use crate::model::Trojan; use anyhow::{Result, bail}; use async_trait::async_trait; /// A verified local proxy connection owned by a runtime probe session. pub struct ProbeConnection<'a> { pub proxy_url: &'a str, pub certificate: &'a str, } #[async_trait] pub trait ProbeSession: Send { fn connection(&self) -> ProbeConnection<'_>; async fn stop(self: Box); } #[async_trait] pub trait Runtime: Send { /// Protection must be installed before durable enabled intent changes. async fn arm(&mut self) -> Result<()>; async fn apply(&mut self, connection: Option<&Trojan>, generation: u64) -> Result<()>; async fn block(&mut self) -> Result<()> { self.arm().await?; self.apply(None, 0).await } async fn maintain(&mut self, connection: Option<&Trojan>, generation: u64) -> Result<()> { self.apply(connection, generation).await } async fn probe(&mut self, _: &Trojan, _: u64) -> Result> { bail!("Protected diagnostic probes are unavailable in this runtime") } /// Called only after disabled intent has been durably recorded. async fn disable(&mut self) -> Result<()>; fn routing(&self) -> &str; } /// Allows managing saved subscriptions without claiming that host capture is available. pub struct OfflineRuntime; #[async_trait] impl Runtime for OfflineRuntime { async fn arm(&mut self) -> Result<()> { bail!("Host networking is unavailable; install and start the Roentgen service") } async fn apply(&mut self, _: Option<&Trojan>, _: u64) -> Result<()> { bail!("Host networking is unavailable") } async fn disable(&mut self) -> Result<()> { Ok(()) } fn routing(&self) -> &str { "unavailable" } }