1use super::{Encoding, FromReq, FromRes, IntoReq, IntoRes};
2use crate::{
3 error::{FromServerFnError, IntoAppError, ServerFnErrorErr},
4 request::{ClientReq, Req},
5 response::{ClientRes, TryRes},
6 ContentType, Decodes, Encodes,
7};
8use std::marker::PhantomData;
9
10pub struct Patch<Codec>(PhantomData<Codec>);
12
13impl<Codec: ContentType> ContentType for Patch<Codec> {
14 const CONTENT_TYPE: &'static str = Codec::CONTENT_TYPE;
15}
16
17impl<Codec: ContentType> Encoding for Patch<Codec> {
18 const METHOD: http::Method = http::Method::PATCH;
19}
20
21impl<E, T, Encoding, Request> IntoReq<Patch<Encoding>, Request, E> for T
22where
23 Request: ClientReq<E>,
24 Encoding: Encodes<T>,
25 E: FromServerFnError,
26{
27 fn into_req(self, path: &str, accepts: &str) -> Result<Request, E> {
28 let data = Encoding::encode(&self).map_err(|e| {
29 ServerFnErrorErr::Serialization(e.to_string()).into_app_error()
30 })?;
31 Request::try_new_patch_bytes(
32 path,
33 accepts,
34 Encoding::CONTENT_TYPE,
35 data,
36 )
37 }
38}
39
40impl<E, T, Request, Encoding> FromReq<Patch<Encoding>, Request, E> for T
41where
42 Request: Req<E> + Send + 'static,
43 Encoding: Decodes<T>,
44 E: FromServerFnError,
45{
46 async fn from_req(req: Request) -> Result<Self, E> {
47 let data = req.try_into_bytes().await?;
48 let s = Encoding::decode(data).map_err(|e| {
49 ServerFnErrorErr::Deserialization(e.to_string()).into_app_error()
50 })?;
51 Ok(s)
52 }
53}
54
55impl<E, Response, Encoding, T> IntoRes<Patch<Encoding>, Response, E> for T
56where
57 Response: TryRes<E>,
58 Encoding: Encodes<T>,
59 E: FromServerFnError + Send,
60 T: Send,
61{
62 async fn into_res(self) -> Result<Response, E> {
63 let data = Encoding::encode(&self).map_err(|e| {
64 ServerFnErrorErr::Serialization(e.to_string()).into_app_error()
65 })?;
66 Response::try_from_bytes(Encoding::CONTENT_TYPE, data)
67 }
68}
69
70impl<E, Encoding, Response, T> FromRes<Patch<Encoding>, Response, E> for T
71where
72 Response: ClientRes<E> + Send,
73 Encoding: Decodes<T>,
74 E: FromServerFnError,
75{
76 async fn from_res(res: Response) -> Result<Self, E> {
77 let data = res.try_into_bytes().await?;
78 let s = Encoding::decode(data).map_err(|e| {
79 ServerFnErrorErr::Deserialization(e.to_string()).into_app_error()
80 })?;
81 Ok(s)
82 }
83}