cyfs_base/objects/
standard.rs

1use crate::*;
2
3#[derive(Clone, Debug)]
4pub enum StandardObject {
5    Device(Device),
6    People(People),
7    SimpleGroup(SimpleGroup),
8    Org(Org),
9    AppGroup(AppGroup),
10    UnionAccount(UnionAccount),
11    ChunkId(ChunkId),
12    File(File),
13    Dir(Dir),
14    Diff(Diff),
15    ProofOfService(ProofOfService),
16    Tx(Tx),
17    Action(Action),
18    ObjectMap(ObjectMap),
19    Contract(Contract),
20}
21
22#[macro_export]
23macro_rules! match_standard_obj {
24    ($on:ident, $o:ident, $body:tt, $chunk_id:ident, $chunk_body:tt) => {
25        match $on {
26            StandardObject::Device($o) => $body,
27            StandardObject::People($o) => $body,
28            StandardObject::SimpleGroup($o) => $body,
29            StandardObject::Org($o) => $body,
30            StandardObject::AppGroup($o) => $body,
31            StandardObject::UnionAccount($o) => $body,
32            StandardObject::ChunkId($chunk_id) => $chunk_body,
33            StandardObject::File($o) => $body,
34            StandardObject::Dir($o) => $body,
35            StandardObject::Diff($o) => $body,
36            StandardObject::ProofOfService($o) => $body,
37            StandardObject::Tx($o) => $body,
38            StandardObject::Action($o) => $body,
39            StandardObject::ObjectMap($o) => $body,
40            StandardObject::Contract($o) => $body,
41        }
42    };
43}
44
45macro_rules! match_standard_owner_obj {
46    ($on:ident, $o:ident, $body:tt, $other_body:tt) => {
47        match $on {
48            StandardObject::Device($o) => $body,
49            StandardObject::People($o) => $body,
50            StandardObject::Contract($o) => $body,
51            StandardObject::File($o) => $body,
52            StandardObject::Dir($o) => $body,
53            StandardObject::Diff($o) => $body,
54            StandardObject::ProofOfService($o) => $body,
55            StandardObject::Action($o) => $body,
56            StandardObject::ObjectMap($o) => $body,
57            _ => $other_body,
58        }
59    };
60}
61
62macro_rules! match_standard_pubkey_obj {
63    ($on:ident, $o:ident, $body:tt, $other_body:tt) => {
64        match $on {
65            StandardObject::Device($o) => $body,
66            StandardObject::People($o) => $body,
67            StandardObject::SimpleGroup($o) => $body,
68            _ => $other_body,
69        }
70    };
71}
72
73macro_rules! match_standard_author_obj {
74    ($on:ident, $o:ident, $body:tt, $other_body:tt) => {
75        match $on {
76            StandardObject::File($o) => $body,
77            StandardObject::Contract($o) => $body,
78            _ => $other_body,
79        }
80    };
81}
82
83macro_rules! match_standard_ood_list_obj {
84    ($on:ident, $o:ident, $body:tt, $other_body:tt) => {
85        match $on {
86            StandardObject::SimpleGroup($o) => $body,
87            StandardObject::People($o) => $body,
88            _ => $other_body,
89        }
90    };
91}
92
93impl StandardObject {
94    pub fn calculate_id(&self) -> ObjectId {
95        match_standard_obj!(self, o, { o.desc().calculate_id() }, chunk_id, {
96            chunk_id.object_id()
97        })
98    }
99
100    pub fn obj_type(&self) -> BuckyResult<u16> {
101        match_standard_obj!(self, o, { Ok(o.desc().obj_type()) }, _chunk_id, {
102            Ok(ObjectTypeCode::Chunk.to_u16())
103        })
104    }
105
106    pub fn obj_type_code(&self) -> ObjectTypeCode {
107        match_standard_obj!(self, o, { o.desc().obj_type_code() }, _chunk_id, {
108            ObjectTypeCode::Chunk
109        })
110    }
111
112    pub fn dec_id(&self) -> &Option<ObjectId> {
113        match_standard_obj!(self, o, { o.desc().dec_id() }, _chunk_id, { &None })
114    }
115
116    pub fn owner(&self) -> &Option<ObjectId> {
117        match_standard_owner_obj!(self, o, { o.desc().owner() }, { &None })
118    }
119
120    pub fn prev(&self) -> &Option<ObjectId> {
121        match_standard_owner_obj!(self, o, { o.desc().prev() }, { &None })
122    }
123
124    pub fn public_key(&self) -> Option<PublicKeyRef> {
125        match_standard_pubkey_obj!(self, o, { o.desc().public_key_ref() }, { None })
126    }
127
128    pub fn author(&self) -> &Option<ObjectId> {
129        match_standard_author_obj!(self, o, { o.desc().author() }, { &None })
130    }
131
132    pub fn ood_list(&self) -> BuckyResult<&Vec<DeviceId>> {
133        match_standard_ood_list_obj!(
134            self,
135            o,
136            {
137                let b = o.body().as_ref();
138                if b.is_none() {
139                    Err(BuckyError::new(BuckyErrorCode::NotFound, "missing body"))
140                } else {
141                    let b = b.unwrap();
142                    Ok(b.content().ood_list())
143                }
144            },
145            {
146                Err(BuckyError::new(
147                    BuckyErrorCode::NotSupport,
148                    "ood_list not support",
149                ))
150            }
151        )
152    }
153
154    pub fn ood_work_mode(&self) -> BuckyResult<OODWorkMode> {
155        match_standard_ood_list_obj!(
156            self,
157            o,
158            {
159                let b = o.body().as_ref();
160                if b.is_none() {
161                    Err(BuckyError::new(BuckyErrorCode::NotFound, "missing body"))
162                } else {
163                    let b = b.unwrap();
164                    Ok(b.content().ood_work_mode())
165                }
166            },
167            {
168                Err(BuckyError::new(
169                    BuckyErrorCode::NotSupport,
170                    "ood_work_mode not support",
171                ))
172            }
173        )
174    }
175
176    pub fn set_body_expect(&mut self, other: &Self) {
177        match self {
178            Self::Device(o) => match other {
179                Self::Device(other) => {
180                    *o.body_mut() = other.body().clone();
181                }
182                _ => unreachable!(),
183            },
184            Self::People(o) => match other {
185                Self::People(other) => {
186                    *o.body_mut() = other.body().clone();
187                }
188                _ => unreachable!(),
189            },
190            Self::SimpleGroup(o) => match other {
191                Self::SimpleGroup(other) => {
192                    *o.body_mut() = other.body().clone();
193                }
194                _ => unreachable!(),
195            },
196            Self::Org(o) => match other {
197                Self::Org(other) => {
198                    *o.body_mut() = other.body().clone();
199                }
200                _ => unreachable!(),
201            },
202            Self::AppGroup(o) => match other {
203                Self::AppGroup(other) => {
204                    *o.body_mut() = other.body().clone();
205                }
206                _ => unreachable!(),
207            },
208            Self::UnionAccount(o) => match other {
209                Self::UnionAccount(other) => {
210                    *o.body_mut() = other.body().clone();
211                }
212                _ => unreachable!(),
213            },
214            Self::File(o) => match other {
215                Self::File(other) => {
216                    *o.body_mut() = other.body().clone();
217                }
218                _ => unreachable!(),
219            },
220            Self::Dir(o) => match other {
221                Self::Dir(other) => {
222                    *o.body_mut() = other.body().clone();
223                }
224                _ => unreachable!(),
225            },
226            Self::Diff(o) => match other {
227                Self::Diff(other) => {
228                    *o.body_mut() = other.body().clone();
229                }
230                _ => unreachable!(),
231            },
232            Self::ProofOfService(o) => match other {
233                Self::ProofOfService(other) => {
234                    *o.body_mut() = other.body().clone();
235                }
236                _ => unreachable!(),
237            },
238            Self::Tx(o) => match other {
239                Self::Tx(other) => {
240                    *o.body_mut() = other.body().clone();
241                }
242                _ => unreachable!(),
243            },
244            Self::Action(o) => match other {
245                Self::Action(other) => {
246                    *o.body_mut() = other.body().clone();
247                }
248                _ => unreachable!(),
249            },
250            Self::ObjectMap(o) => match other {
251                Self::ObjectMap(other) => {
252                    *o.body_mut() = other.body().clone();
253                }
254                _ => unreachable!(),
255            },
256            Self::Contract(o) => match other {
257                Self::Contract(other) => {
258                    *o.body_mut() = other.body().clone();
259                }
260                _ => unreachable!(),
261            },
262            Self::ChunkId(_) => {
263                unreachable!();
264            }
265        }
266    }
267}
268
269impl RawEncode for StandardObject {
270    fn raw_measure(&self, purpose: &Option<RawEncodePurpose>) -> BuckyResult<usize> {
271        match self {
272            StandardObject::Device(o) => o.raw_measure(purpose),
273            StandardObject::People(o) => o.raw_measure(purpose),
274            StandardObject::SimpleGroup(o) => o.raw_measure(purpose),
275            StandardObject::Org(o) => o.raw_measure(purpose),
276            StandardObject::AppGroup(o) => o.raw_measure(purpose),
277            StandardObject::UnionAccount(o) => o.raw_measure(purpose),
278            StandardObject::ChunkId(o) => o.raw_measure(purpose),
279            StandardObject::File(o) => o.raw_measure(purpose),
280            StandardObject::Dir(o) => o.raw_measure(purpose),
281            StandardObject::Diff(o) => o.raw_measure(purpose),
282            StandardObject::ProofOfService(o) => o.raw_measure(purpose),
283            StandardObject::Tx(o) => o.raw_measure(purpose),
284            StandardObject::Action(o) => o.raw_measure(purpose),
285            StandardObject::ObjectMap(o) => o.raw_measure(purpose),
286            StandardObject::Contract(o) => o.raw_measure(purpose),
287        }
288    }
289
290    fn raw_encode<'a>(
291        &self,
292        buf: &'a mut [u8],
293        purpose: &Option<RawEncodePurpose>,
294    ) -> BuckyResult<&'a mut [u8]> {
295        match self {
296            StandardObject::Device(o) => o.raw_encode(buf, purpose),
297            StandardObject::People(o) => o.raw_encode(buf, purpose),
298            StandardObject::SimpleGroup(o) => o.raw_encode(buf, purpose),
299            StandardObject::Org(o) => o.raw_encode(buf, purpose),
300            StandardObject::AppGroup(o) => o.raw_encode(buf, purpose),
301            StandardObject::UnionAccount(o) => o.raw_encode(buf, purpose),
302            StandardObject::ChunkId(o) => o.raw_encode(buf, purpose),
303            StandardObject::File(o) => o.raw_encode(buf, purpose),
304            StandardObject::Dir(o) => o.raw_encode(buf, purpose),
305            StandardObject::Diff(o) => o.raw_encode(buf, purpose),
306            StandardObject::ProofOfService(o) => o.raw_encode(buf, purpose),
307            StandardObject::Tx(o) => o.raw_encode(buf, purpose),
308            StandardObject::Action(o) => o.raw_encode(buf, purpose),
309            StandardObject::ObjectMap(o) => o.raw_encode(buf, purpose),
310            StandardObject::Contract(o) => o.raw_encode(buf, purpose),
311        }
312    }
313}
314
315// 通用的单个对象解码器
316impl<'de> RawDecode<'de> for StandardObject {
317    fn raw_decode(buf: &'de [u8]) -> BuckyResult<(Self, &'de [u8])> {
318        let (ctx, _) = NamedObjectContext::raw_decode(buf).map_err(|e| {
319            log::error!("StandardObject::raw_decode/NamedObjectContext error:{}", e);
320            e
321        })?;
322
323        match ctx.obj_type_code() {
324            ObjectTypeCode::Device => {
325                Device::raw_decode(buf).map(|(obj, buf)| (StandardObject::Device(obj), buf))
326            }
327            ObjectTypeCode::People => {
328                People::raw_decode(buf).map(|(obj, buf)| (StandardObject::People(obj), buf))
329            }
330            ObjectTypeCode::SimpleGroup => SimpleGroup::raw_decode(buf)
331                .map(|(obj, buf)| (StandardObject::SimpleGroup(obj), buf)),
332            ObjectTypeCode::Org => {
333                Org::raw_decode(buf).map(|(obj, buf)| (StandardObject::Org(obj), buf))
334            }
335            ObjectTypeCode::AppGroup => {
336                AppGroup::raw_decode(buf).map(|(obj, buf)| (StandardObject::AppGroup(obj), buf))
337            }
338            ObjectTypeCode::UnionAccount => UnionAccount::raw_decode(buf)
339                .map(|(obj, buf)| (StandardObject::UnionAccount(obj), buf)),
340            ObjectTypeCode::Chunk => {
341                ChunkId::raw_decode(buf).map(|(obj, buf)| (StandardObject::ChunkId(obj), buf))
342            }
343            ObjectTypeCode::File => {
344                File::raw_decode(buf).map(|(obj, buf)| (StandardObject::File(obj), buf))
345            }
346            ObjectTypeCode::Dir => {
347                Dir::raw_decode(buf).map(|(obj, buf)| (StandardObject::Dir(obj), buf))
348            }
349            ObjectTypeCode::Diff => {
350                Diff::raw_decode(buf).map(|(obj, buf)| (StandardObject::Diff(obj), buf))
351            }
352            ObjectTypeCode::ProofOfService => ProofOfService::raw_decode(buf)
353                .map(|(obj, buf)| (StandardObject::ProofOfService(obj), buf)),
354            ObjectTypeCode::Tx => {
355                Tx::raw_decode(buf).map(|(obj, buf)| (StandardObject::Tx(obj), buf))
356            }
357            ObjectTypeCode::Action => {
358                Action::raw_decode(buf).map(|(obj, buf)| (StandardObject::Action(obj), buf))
359            }
360            ObjectTypeCode::ObjectMap => {
361                ObjectMap::raw_decode(buf).map(|(obj, buf)| (StandardObject::ObjectMap(obj), buf))
362            }
363            ObjectTypeCode::Contract => {
364                Contract::raw_decode(buf).map(|(obj, buf)| (StandardObject::Contract(obj), buf))
365            }
366            _ => {
367                unreachable!();
368            }
369        }
370    }
371}