modular_rs/core/
module.rs

1use crate::core::error::ModuleError;
2use crate::core::modules::{BoxModuleService, ModuleRequest, ModuleResponse};
3use futures_util::future::BoxFuture;
4use futures_util::TryFutureExt;
5use std::marker::PhantomData;
6use std::sync::Weak;
7use std::task::{Context, Poll};
8use tokio::sync::Mutex;
9use tower::Service;
10
11#[derive(Clone)]
12pub struct Module<Request, Response>(pub(crate) Weak<Mutex<BoxModuleService<Request, Response>>>);
13
14impl<Request, Response> Module<Request, Response> {
15    pub async fn invoke(
16        &self,
17        req: ModuleRequest<Request>,
18    ) -> Result<ModuleResponse<Response>, ModuleError> {
19        let module = match self.0.upgrade() {
20            Some(v) => v,
21            None => {
22                return Err(ModuleError::Destroyed);
23            }
24        };
25
26        let mut v = module.lock().await;
27        v.call(req).await
28    }
29}
30
31#[repr(transparent)]
32pub(crate) struct ModuleService<S, Req, Request, Response>(
33    pub S,
34    pub PhantomData<(Req, Request, Response)>,
35)
36where
37    S: Service<Req> + Send + 'static,
38    Req: From<ModuleRequest<Request>> + Send,
39    S::Error: Into<ModuleError> + Send + 'static,
40    S::Response: Into<ModuleResponse<Response>> + Send + 'static,
41    S::Future: Send + Sync;
42
43impl<S, Req, Request, Response> Service<ModuleRequest<Request>>
44    for ModuleService<S, Req, Request, Response>
45where
46    S: Service<Req> + Send + 'static,
47    Req: From<ModuleRequest<Request>> + Send,
48    S::Error: Into<ModuleError> + Send + 'static,
49    S::Response: Into<ModuleResponse<Response>> + Send + 'static,
50    S::Future: Send + Sync + 'static,
51    Response: 'static,
52{
53    type Response = ModuleResponse<Response>;
54    type Error = ModuleError;
55    type Future = BoxFuture<'static, Result<Self::Response, Self::Error>>;
56
57    #[inline(always)]
58    fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll<Result<(), Self::Error>> {
59        self.0.poll_ready(cx).map_err(Into::into)
60    }
61
62    #[inline(always)]
63    fn call(&mut self, req: ModuleRequest<Request>) -> Self::Future {
64        Box::pin(
65            self.0
66                .call(req.into())
67                .map_ok(Into::into)
68                .map_err(Into::into),
69        )
70    }
71}