stratus/eth/primitives/
execution_value_change.rs1use std::fmt::Debug;
6
7use display_json::DebugAsJson;
8
9use crate::ext::to_json_string;
10
11#[derive(Clone, PartialEq, Eq, fake::Dummy, serde::Serialize, serde::Deserialize, Default)]
13pub struct ExecutionValueChange<T>
14where
15 T: PartialEq + serde::Serialize,
16{
17 original: ValueState<T>,
18 modified: ValueState<T>,
19}
20
21impl<T> Copy for ExecutionValueChange<T> where T: Copy + PartialEq + serde::Serialize {}
22
23impl<T> From<T> for ExecutionValueChange<T>
24where
25 T: PartialEq + serde::Serialize,
26{
27 fn from(value: T) -> Self {
28 Self::from_modified(value)
29 }
30}
31
32impl<T> Debug for ExecutionValueChange<T>
33where
34 T: PartialEq + serde::Serialize,
35{
36 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
37 f.write_str(&to_json_string(self))
38 }
39}
40
41impl<T> ExecutionValueChange<T>
42where
43 T: PartialEq + serde::Serialize,
44{
45 pub fn from_original(value: T) -> Self {
47 Self {
48 original: ValueState::Set(value),
49 modified: ValueState::NotSet,
50 }
51 }
52
53 pub fn from_modified(value: T) -> Self {
55 Self {
56 original: ValueState::NotSet,
57 modified: ValueState::Set(value),
58 }
59 }
60
61 pub fn set_modified(&mut self, value: T) {
63 self.modified = ValueState::Set(value);
64 }
65
66 pub fn set_original(&mut self, value: T) {
67 self.original = ValueState::Set(value);
68 }
69
70 pub fn take_original_ref(&self) -> Option<&T> {
72 self.original.take_ref()
73 }
74
75 pub fn take_modified(self) -> Option<T> {
77 self.modified.take()
78 }
79
80 pub fn take_modified_ref(&self) -> Option<&T> {
82 self.modified.take_ref()
83 }
84
85 pub fn take(self) -> Option<T> {
87 self.modified.take().or_else(|| self.original.take())
88 }
89
90 pub fn take_ref(&self) -> Option<&T> {
92 self.modified.take_ref().or_else(|| self.original.take_ref())
93 }
94
95 pub fn is_modified(&self) -> bool {
97 self.modified.is_set() && (self.original != self.modified)
98 }
99
100 pub fn is_empty(&self) -> bool {
101 !self.modified.is_set() && !self.original.is_set()
102 }
103}
104
105impl<T> From<Option<T>> for ExecutionValueChange<T>
106where
107 T: PartialEq + serde::Serialize,
108{
109 fn from(value: Option<T>) -> Self {
110 let modified = match value {
111 None => ValueState::NotSet,
112 Some(value) => ValueState::Set(value),
113 };
114 ExecutionValueChange {
115 original: ValueState::NotSet,
116 modified,
117 }
118 }
119}
120
121#[derive(DebugAsJson, Clone, PartialEq, Eq, fake::Dummy, serde::Serialize, serde::Deserialize, Default)]
126#[serde(rename_all = "snake_case")]
127pub enum ValueState<T> {
128 Set(T),
129 #[default]
130 NotSet,
131}
132
133impl<T> Copy for ValueState<T> where T: Copy {}
134
135impl<T> ValueState<T> {
136 pub fn is_set(&self) -> bool {
137 matches!(self, Self::Set(_))
138 }
139
140 pub fn take(self) -> Option<T> {
141 if let Self::Set(value) = self { Some(value) } else { None }
142 }
143
144 pub fn take_ref(&self) -> Option<&T> {
145 if let Self::Set(value) = self { Some(value) } else { None }
146 }
147}