mincat_core/
handler.rs

1use std::{collections::VecDeque, fmt::Debug, future::Future, marker::PhantomData};
2
3use mincat_macro::repeat_macro_max_generics_param;
4
5use crate::{
6    middleware::Middleware,
7    next::Next,
8    request::{FromRequest, FromRequestParts, Request},
9    response::{IntoResponse, Response},
10};
11
12#[derive(Clone)]
13pub struct Handler {
14    pub func: Box<dyn HandlerFunc>,
15    pub middleware: Option<VecDeque<Box<dyn Middleware>>>,
16}
17
18impl Debug for Handler {
19    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
20        let mut middleware_len = 0;
21        if let Some(middleware) = &self.middleware {
22            middleware_len = middleware.len();
23        }
24
25        f.debug_struct("Handler")
26            .field("func", &"func")
27            .field("middleware", &middleware_len)
28            .finish()
29    }
30}
31
32impl Handler {
33    pub fn middleware<T>(&mut self, middleware: T) -> Self
34    where
35        T: Into<Box<dyn Middleware>>,
36    {
37        self.middleware
38            .get_or_insert(VecDeque::new())
39            .push_back(middleware.into());
40
41        self.clone()
42    }
43
44    pub async fn exectue(self, request: Request) -> Response {
45        Next::new(self).run(request).await
46    }
47}
48
49#[async_trait::async_trait]
50pub trait HandlerFunc: Send + Sync {
51    async fn call(self: Box<Self>, request: Request) -> Response;
52
53    fn clone_box(&self) -> Box<dyn HandlerFunc>;
54}
55
56impl Clone for Box<dyn HandlerFunc> {
57    fn clone(&self) -> Self {
58        self.clone_box()
59    }
60}
61
62#[async_trait::async_trait]
63pub trait HandlerFuncParam<Param>: Send {
64    async fn call(self, request: Request) -> Response;
65}
66
67#[derive(Clone)]
68pub struct FuncParamHandler<Func, Param>
69where
70    Func: HandlerFuncParam<Param>,
71{
72    func: Func,
73    _mark: PhantomData<Param>,
74}
75
76impl<Func, Param> From<Func> for FuncParamHandler<Func, Param>
77where
78    Func: HandlerFuncParam<Param>,
79{
80    fn from(value: Func) -> Self {
81        Self {
82            func: value,
83            _mark: PhantomData,
84        }
85    }
86}
87
88impl<Func, Param> From<FuncParamHandler<Func, Param>> for Handler
89where
90    Func: HandlerFuncParam<Param> + Clone + Sync + 'static,
91    Param: Send + Sync + 'static,
92{
93    fn from(value: FuncParamHandler<Func, Param>) -> Self {
94        Handler {
95            func: Box::new(value),
96            middleware: None,
97        }
98    }
99}
100
101#[async_trait::async_trait]
102impl<Func, Param> HandlerFunc for FuncParamHandler<Func, Param>
103where
104    Func: HandlerFuncParam<Param> + Clone + Sync + 'static,
105    Param: Send + Sync + 'static,
106{
107    async fn call(self: Box<Self>, request: Request) -> Response {
108        self.func.call(request).await
109    }
110
111    fn clone_box(&self) -> Box<dyn HandlerFunc> {
112        Box::new(Self {
113            func: self.func.clone(),
114            _mark: PhantomData,
115        })
116    }
117}
118
119#[async_trait::async_trait]
120impl<Func, Fut, Res> HandlerFuncParam<((),)> for Func
121where
122    Func: FnOnce() -> Fut,
123    Func: Clone + Send + Sync + 'static,
124    Fut: Future<Output = Res> + Send,
125    Res: IntoResponse,
126{
127    async fn call(self, _: Request) -> Response {
128        self().await.into_response()
129    }
130}
131
132macro_rules! handle_func_param {
133    ([$($param: ident),*], $lastparam:ident) => {
134        #[allow(non_snake_case)]
135        #[async_trait::async_trait]
136        impl<Func, Fut, Res, $($param,)* $lastparam> HandlerFuncParam<($($param,)* $lastparam,)> for Func
137        where
138            Func: FnOnce($($param,)* $lastparam,) -> Fut,
139            Func: Clone + Send + Sync + 'static,
140            Fut: Future<Output = Res> + Send,
141            Res: IntoResponse,
142            $($param: FromRequestParts + Send,)*
143            $lastparam: FromRequest + Send
144        {
145            async fn call(self, request: Request) -> Response {
146                #[allow(unused_mut)]
147                let (mut parts, body) = request.into_parts();
148
149                $(
150                    let $param = match $param::from_request_parts(&mut parts).await {
151                        Ok(v) => v,
152                        Err(e) => return e.into_response(),
153                    };
154                )*
155
156                let request = Request::from_parts(parts, body);
157
158                let $lastparam = match $lastparam::from_request(request).await {
159                    Ok(v) => v,
160                    Err(e) => return e.into_response(),
161                };
162
163                let res = self($($param,)* $lastparam,).await;
164
165                res.into_response()
166            }
167
168        }
169    }
170}
171
172macro_rules! handle_func_param_pre {
173    ($($param: ident),*) => {
174        handle_func_param!([$($param),*], T);
175    }
176}
177
178repeat_macro_max_generics_param!(handle_func_param_pre, 0, 17, P);