use std::future::Future;
use std::pin::Pin;
use std::sync::Arc;
use crate::horizontal_adapter::{BroadcastMessage, RequestBody, ResponseBody};
use async_trait::async_trait;
use sockudo_core::error::Result;
use sockudo_core::metrics::MetricsInterface;
pub type BoxFuture<'a, T> = Pin<Box<dyn Future<Output = T> + Send + 'a>>;
pub type ResponseHandler = Arc<dyn Fn(ResponseBody) -> BoxFuture<'static, ()> + Send + Sync>;
pub struct InboxGuard {
pub(crate) _cancel: tokio::sync::oneshot::Sender<()>,
}
pub struct TransportHandlers {
pub on_broadcast: Arc<dyn Fn(BroadcastMessage) -> BoxFuture<'static, ()> + Send + Sync>,
pub on_request:
Arc<dyn Fn(RequestBody) -> BoxFuture<'static, Result<ResponseBody>> + Send + Sync>,
pub on_response: Arc<dyn Fn(ResponseBody) -> BoxFuture<'static, ()> + Send + Sync>,
}
#[async_trait]
pub trait HorizontalTransport: Send + Sync + Clone {
type Config: Send + Sync;
async fn new(config: Self::Config) -> Result<Self>;
async fn publish_broadcast(&self, message: &BroadcastMessage) -> Result<()>;
async fn publish_request(&self, request: &RequestBody) -> Result<()>;
async fn publish_response(&self, response: &ResponseBody) -> Result<()>;
async fn start_listeners(&self, handlers: TransportHandlers) -> Result<()>;
async fn get_node_count(&self) -> Result<usize>;
async fn check_health(&self) -> Result<()>;
fn set_metrics(&self, _metrics: Arc<dyn MetricsInterface + Send + Sync>) {}
fn new_inbox(&self) -> Option<String> {
None
}
async fn publish_request_with_reply(
&self,
request: &RequestBody,
_reply_to: &str,
) -> Result<()> {
self.publish_request(request).await
}
async fn subscribe_response_inbox(
&self,
_inbox: &str,
_handler: ResponseHandler,
) -> Result<Option<InboxGuard>> {
Ok(None)
}
}
pub trait TransportConfig: Send + Sync + Clone {
fn request_timeout_ms(&self) -> u64;
fn prefix(&self) -> &str;
}