depo_api/request/
store_share.rs

1use bc_envelope::prelude::*;
2use gstp::prelude::*;
3
4use crate::{
5    DATA_PARAM, DATA_PARAM_NAME, Error, Result, STORE_SHARE_FUNCTION,
6    receipt::Receipt,
7    util::{Abbrev, FlankedFunction},
8};
9
10//
11// Request
12//
13
14#[derive(Debug, Clone, PartialEq, Eq)]
15pub struct StoreShare(ByteString);
16
17impl StoreShare {
18    pub fn new(data: impl Into<ByteString>) -> Self { Self(data.into()) }
19
20    pub fn data(&self) -> &[u8] { self.0.as_ref() }
21}
22
23impl From<StoreShare> for Expression {
24    fn from(value: StoreShare) -> Self {
25        Expression::new(STORE_SHARE_FUNCTION)
26            .with_parameter(DATA_PARAM, value.0)
27    }
28}
29
30impl TryFrom<Expression> for StoreShare {
31    type Error = Error;
32
33    fn try_from(expression: Expression) -> Result<Self> {
34        Ok(Self::new(
35            expression
36                .extract_object_for_parameter::<ByteString>(DATA_PARAM)
37                .map_err(|_e| Error::MissingParameter {
38                    parameter: DATA_PARAM_NAME.to_string(),
39                })?,
40        ))
41    }
42}
43
44impl std::fmt::Display for StoreShare {
45    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
46        f.write_fmt(format_args!(
47            "{} {}",
48            "storeShare".flanked_function(),
49            ByteString::from(self.data()).abbrev()
50        ))
51    }
52}
53
54//
55// Response
56//
57
58#[derive(Debug, Clone, PartialEq, Eq)]
59pub struct StoreShareResult(Receipt);
60
61impl StoreShareResult {
62    pub fn new(receipt: Receipt) -> Self { Self(receipt) }
63
64    pub fn receipt(&self) -> &Receipt { &self.0 }
65}
66
67impl From<StoreShareResult> for Envelope {
68    fn from(value: StoreShareResult) -> Self { value.0.into_envelope() }
69}
70
71impl TryFrom<Envelope> for StoreShareResult {
72    type Error = Error;
73
74    fn try_from(envelope: Envelope) -> Result<Self> {
75        Ok(Self::new(Receipt::try_from(envelope)?))
76    }
77}
78
79impl TryFrom<SealedResponse> for StoreShareResult {
80    type Error = Error;
81
82    fn try_from(response: SealedResponse) -> Result<Self> {
83        response.result()?.clone().try_into()
84    }
85}
86
87impl std::fmt::Display for StoreShareResult {
88    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
89        f.write_fmt(format_args!(
90            "{} OK receipt {}",
91            "storeShare".flanked_function(),
92            self.receipt().abbrev()
93        ))
94    }
95}
96
97#[cfg(test)]
98mod tests {
99    use bc_components::XID;
100    use indoc::indoc;
101
102    use super::*;
103
104    #[test]
105    fn test_request() {
106        bc_envelope::register_tags();
107
108        let data = b"data";
109        let request = StoreShare::new(data);
110        let expression: Expression = request.clone().into();
111        let request_envelope = expression.to_envelope();
112        // println!("{}", request_envelope.format());
113        #[rustfmt::skip]
114        assert_eq!(request_envelope.format(), indoc! {r#"
115            «"storeShare"» [
116                ❰"data"❱: Bytes(4)
117            ]
118        "#}.trim());
119        let decoded_expression =
120            Expression::try_from(request_envelope).unwrap();
121        let decoded = StoreShare::try_from(decoded_expression).unwrap();
122        assert_eq!(request, decoded);
123    }
124
125    #[test]
126    fn test_response() {
127        bc_envelope::register_tags();
128
129        let user_id = XID::from_data_ref(hex_literal::hex!(
130            "8712dfac3d0ebfa910736b2a9ee39d4b68f64222a77bcc0074f3f5f1c9216d30"
131        ))
132        .unwrap();
133        let data = b"data";
134        let receipt = Receipt::new(user_id, data);
135        let result = StoreShareResult::new(receipt);
136        let result_envelope = result.to_envelope();
137        // println!("{}", result_envelope.format());
138        #[rustfmt::skip]
139        assert_eq!(result_envelope.format(), indoc! {r#"
140            Bytes(32) [
141                'isA': "Receipt"
142            ]
143        "#}.trim());
144        let decoded = StoreShareResult::try_from(result_envelope).unwrap();
145        assert_eq!(result, decoded);
146    }
147}