diff options
Diffstat (limited to 'src/endpoint.rs')
-rw-r--r-- | src/endpoint.rs | 39 |
1 files changed, 36 insertions, 3 deletions
diff --git a/src/endpoint.rs b/src/endpoint.rs index 0e1f5c8..adb3532 100644 --- a/src/endpoint.rs +++ b/src/endpoint.rs @@ -12,13 +12,15 @@ use crate::proto::*; use crate::util::*; /// This trait should be implemented by all messages your application -/// wants to handle (click to read more). +/// wants to handle pub trait Message: Serialize + for<'de> Deserialize<'de> + Send + Sync { type Response: Serialize + for<'de> Deserialize<'de> + Send + Sync; } -pub(crate) type DynEndpoint = Box<dyn GenericEndpoint + Send + Sync>; - +/// This trait should be implemented by an object of your application +/// that can handle a message of type `M`. +/// +/// The handler object should be in an Arc, see `Endpoint::set_handler` #[async_trait] pub trait EndpointHandler<M>: Send + Sync where @@ -27,6 +29,27 @@ where async fn handle(self: &Arc<Self>, m: M, from: NodeID) -> M::Response; } +/// If one simply wants to use an endpoint in a client fashion, +/// without locally serving requests to that endpoint, +/// use the unit type `()` as the handler type: +/// it will panic if it is ever made to handle request. +#[async_trait] +impl<M: Message + 'static> EndpointHandler<M> for () { + async fn handle(self: &Arc<()>, _m: M, _from: NodeID) -> M::Response { + panic!("This endpoint should not have a local handler."); + } +} + +/// This struct represents an endpoint for message of type `M`. +/// +/// Creating a new endpoint is done by calling `NetApp::endpoint`. +/// An endpoint is identified primarily by its path, which is specified +/// at creation time. +/// +/// An `Endpoint` is used both to send requests to remote nodes, +/// and to specify the handler for such requests on the local node. +/// The type `H` represents the type of the handler object for +/// endpoint messages (see `EndpointHandler`). pub struct Endpoint<M, H> where M: Message, @@ -51,9 +74,15 @@ where handler: ArcSwapOption::from(None), } } + + /// Set the object that is responsible of handling requests to + /// this endpoint on the local node. pub fn set_handler(&self, h: Arc<H>) { self.handler.swap(Some(h)); } + + /// Call this endpoint on a remote node (or on the local node, + /// for that matter) pub async fn call( &self, target: &NodeID, @@ -84,6 +113,10 @@ where } } +// ---- Internal stuff ---- + +pub(crate) type DynEndpoint = Box<dyn GenericEndpoint + Send + Sync>; + #[async_trait] pub(crate) trait GenericEndpoint { async fn handle(&self, buf: &[u8], from: NodeID) -> Result<Vec<u8>, Error>; |