tosic_http/extractors/
json.rs

1//! Json extractor
2
3use crate::body::message_body::MessageBody;
4use crate::body::BoxBody;
5use crate::error::ServerError;
6use crate::extractors::ExtractionError;
7use crate::futures::{err, ok, Ready};
8use crate::traits::from_request::FromRequest;
9use serde::de::DeserializeOwned;
10use std::fmt::Debug;
11
12#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord)]
13/// Json extractor to extract data from the request
14pub struct Json<V>(pub V);
15
16impl<V: DeserializeOwned> FromRequest for Json<V> {
17    type Error = ServerError;
18    type Future = Ready<Result<Json<V>, Self::Error>>;
19    fn from_request(
20        _: &crate::request::HttpRequest,
21        payload: &mut crate::request::HttpPayload,
22    ) -> Self::Future {
23        let body = <BoxBody as Clone>::clone(payload)
24            .boxed()
25            .try_into_bytes()
26            .expect("Unable to read body");
27
28        match serde_json::from_slice(&body) {
29            Ok(value) => ok(Json(value)),
30            Err(error) => err(ServerError::ExtractionError(ExtractionError::Json(error))),
31        }
32    }
33}
34
35impl<T> Json<T> {
36    #[inline]
37    /// Returns the inner value
38    pub fn into_inner(self) -> T {
39        self.0
40    }
41}
42
43impl<T> std::ops::Deref for Json<T> {
44    type Target = T;
45
46    #[inline]
47    fn deref(&self) -> &Self::Target {
48        &self.0
49    }
50}
51
52impl<T> std::ops::DerefMut for Json<T> {
53    #[inline]
54    fn deref_mut(&mut self) -> &mut Self::Target {
55        &mut self.0
56    }
57}