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
315impl<'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}