1use serde::{Deserialize, Serialize};
2
3#[cfg(feature = "cid_debug_trace")]
4pub(crate) use cid_debug_trace::*;
5
6#[derive(Clone, Copy, Eq, PartialEq, Hash, Default, PartialOrd, Ord, Serialize, Deserialize)]
10#[repr(transparent)]
11pub struct Cid(pub [u8; 32]);
12
13impl std::fmt::Display for Cid {
14 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
15 write!(f, "{}", bs58::encode(self.0).into_string())
16 }
17}
18
19impl std::fmt::Debug for Cid {
20 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
21 write!(f, "Cid({})", self)
22 }
23}
24
25impl Cid {
26 pub fn update(&mut self, bytes: &[u8]) {
28 use sha2::Digest;
29 let pre_hash = self.0;
30 let mut hasher = sha2::Sha256::new();
31 hasher.update(pre_hash);
32 hasher.update(bytes);
33 let result = hasher.finalize();
34 self.0.copy_from_slice(&result);
35 }
36}
37
38#[cfg(feature = "cid_debug_trace")]
39mod cid_debug_trace {
40
41 use crate::{AssetLoc, Cid};
42 use std::path::Path;
43
44 use bones_utils::default;
45 use ustr::Ustr;
46
47 pub(crate) struct CidDebugTrace<'a> {
48 pub schema_full_name: Ustr,
49 pub file_path: &'a Path,
50
51 pub cid_after_schema_fullname: Cid,
52 pub cid_after_contents: Cid,
53
54 pub cid_after_deps: Vec<(Cid, Cid, Option<AssetLoc>)>,
56
57 pub final_cid: Cid,
58 }
59
60 impl<'a> CidDebugTrace<'a> {
61 pub(crate) fn new(schema_full_name: Ustr, file_path: &'a Path) -> Self {
62 Self {
63 schema_full_name,
64 file_path,
65 cid_after_schema_fullname: default(),
66 cid_after_contents: default(),
67 cid_after_deps: default(),
68 final_cid: default(),
69 }
70 }
71 }
72
73 impl<'a> std::fmt::Display for CidDebugTrace<'a> {
74 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
75 writeln!(
77 f,
78 "Cid trace schema: {:?} file path: {:?}",
79 self.schema_full_name, self.file_path
80 )?;
81 writeln!(f, "Trace is in order of updates, which impacts result")?;
82
83 writeln!(
85 f,
86 "[Intermediate] Cid from schema fullname: {:?} cid: {}",
87 self.schema_full_name, self.cid_after_schema_fullname
88 )?;
89
90 writeln!(
92 f,
93 "[Intermediate] Cid from contents: cid: {}",
94 self.cid_after_contents
95 )?;
96
97 writeln!(f, "Dumping updates from sorted dependency cids:")?;
99 for (dep_cid, updated_cid, dep_asset_loc) in self.cid_after_deps.iter() {
100 writeln!(
101 f,
102 " dep_cid: {}, cid: {}, dep_asset_loc: {:?}",
103 dep_cid, updated_cid, dep_asset_loc
104 )?;
105 }
106
107 writeln!(f, "Final cid: {}", self.final_cid)?;
109
110 Ok(())
111 }
112 }
113}