1#[derive(Clone, Debug, Default, Eq, PartialEq)]
43#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))]
44#[cfg_attr(feature = "proptest", derive(test_strategy::Arbitrary))]
45#[cfg_attr(feature = "bcs-schema", derive(iota_bcs_schema::BcsSchema))]
46pub struct GasCostSummary {
47 #[cfg_attr(feature = "serde", serde(with = "crate::_serde::ReadableDisplay"))]
49 pub computation_cost: u64,
50 #[cfg_attr(feature = "serde", serde(with = "crate::_serde::ReadableDisplay"))]
52 pub computation_cost_burned: u64,
53 #[cfg_attr(feature = "serde", serde(with = "crate::_serde::ReadableDisplay"))]
56 pub storage_cost: u64,
57 #[cfg_attr(feature = "serde", serde(with = "crate::_serde::ReadableDisplay"))]
60 pub storage_rebate: u64,
61 #[cfg_attr(feature = "serde", serde(with = "crate::_serde::ReadableDisplay"))]
64 pub non_refundable_storage_fee: u64,
65}
66
67impl GasCostSummary {
68 pub fn new(
79 computation_cost: u64,
80 computation_cost_burned: u64,
81 storage_cost: u64,
82 storage_rebate: u64,
83 non_refundable_storage_fee: u64,
84 ) -> GasCostSummary {
85 GasCostSummary {
86 computation_cost,
87 computation_cost_burned,
88 storage_cost,
89 storage_rebate,
90 non_refundable_storage_fee,
91 }
92 }
93
94 pub fn gas_used(&self) -> u64 {
96 self.computation_cost
97 .checked_add(self.storage_cost)
98 .expect("gas_used overflow")
99 }
100
101 pub fn net_gas_usage(&self) -> i64 {
104 (self.gas_used() as i64)
105 .checked_sub(self.storage_rebate as i64)
106 .expect("net_gas_usage underflow")
107 }
108}
109
110impl std::ops::AddAssign<&Self> for GasCostSummary {
111 fn add_assign(&mut self, other: &Self) {
112 self.computation_cost = self
113 .computation_cost
114 .checked_add(other.computation_cost)
115 .expect("computation_cost overflow");
116 self.computation_cost_burned = self
117 .computation_cost_burned
118 .checked_add(other.computation_cost_burned)
119 .expect("computation_cost_burned overflow");
120 self.storage_cost = self
121 .storage_cost
122 .checked_add(other.storage_cost)
123 .expect("storage_cost overflow");
124 self.storage_rebate = self
125 .storage_rebate
126 .checked_add(other.storage_rebate)
127 .expect("storage_rebate overflow");
128 self.non_refundable_storage_fee = self
129 .non_refundable_storage_fee
130 .checked_add(other.non_refundable_storage_fee)
131 .expect("non_refundable_storage_fee overflow");
132 }
133}
134
135impl std::ops::SubAssign<&Self> for GasCostSummary {
136 fn sub_assign(&mut self, other: &Self) {
137 self.computation_cost = self
138 .computation_cost
139 .checked_sub(other.computation_cost)
140 .expect("computation_cost underflow");
141 self.computation_cost_burned = self
142 .computation_cost_burned
143 .checked_sub(other.computation_cost_burned)
144 .expect("computation_cost_burned underflow");
145 self.storage_cost = self
146 .storage_cost
147 .checked_sub(other.storage_cost)
148 .expect("storage_cost underflow");
149 self.storage_rebate = self
150 .storage_rebate
151 .checked_sub(other.storage_rebate)
152 .expect("storage_rebate underflow");
153 self.non_refundable_storage_fee = self
154 .non_refundable_storage_fee
155 .checked_sub(other.non_refundable_storage_fee)
156 .expect("non_refundable_storage_fee underflow");
157 }
158}
159
160impl std::ops::AddAssign<Self> for GasCostSummary {
161 fn add_assign(&mut self, other: Self) {
162 self.add_assign(&other);
163 }
164}
165
166impl std::ops::SubAssign<Self> for GasCostSummary {
167 fn sub_assign(&mut self, other: Self) {
168 self.sub_assign(&other);
169 }
170}
171
172impl crate::TreeDisplay for GasCostSummary {
173 fn fmt_tree(&self, w: &mut crate::TreeWriter<'_, '_>) -> std::fmt::Result {
174 w.header("Gas Cost Summary")?;
175 w.leaf("Computation Cost", &self.computation_cost, false)?;
176 w.leaf(
177 "Computation Cost Burned",
178 &self.computation_cost_burned,
179 false,
180 )?;
181 w.leaf("Storage Cost", &self.storage_cost, false)?;
182 w.leaf("Storage Rebate", &self.storage_rebate, false)?;
183 w.leaf(
184 "Non-Refundable Storage Fee",
185 &self.non_refundable_storage_fee,
186 true,
187 )
188 }
189}
190
191crate::impl_tree_display!(GasCostSummary);
192
193#[cfg(all(test, feature = "serde"))]
194mod tests {
195 #[cfg(target_arch = "wasm32")]
196 use wasm_bindgen_test::wasm_bindgen_test as test;
197
198 use super::*;
199
200 #[test]
201 fn formats() {
202 let actual = GasCostSummary {
203 computation_cost: 42,
204 computation_cost_burned: 24,
205 storage_cost: u64::MAX,
206 storage_rebate: 0,
207 non_refundable_storage_fee: 9,
208 };
209
210 println!("{}", serde_json::to_string(&actual).unwrap());
211 println!("{:?}", bcs::to_bytes(&actual).unwrap());
212 }
213}