Skip to content

Commit 353604f

Browse files
authored
Merge pull request #193 from openmina/refactor/inlined-actions
Refactor: Inline action group definitions into the parent enum type (first pass)
2 parents 0c07bdd + 35fa4f4 commit 353604f

File tree

54 files changed

+2376
-4157
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

54 files changed

+2376
-4157
lines changed

node/build.rs

Lines changed: 104 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -48,16 +48,53 @@ fn is_same_file<P: AsRef<Path>>(file1: P, file2: P) -> Result<bool, std::io::Err
4848
Ok(b1 == b2)
4949
}
5050

51+
#[derive(Debug, Clone)]
52+
enum EnumElement {
53+
InlineFields {
54+
tag: String,
55+
action_kind: String,
56+
has_fields: bool,
57+
},
58+
Nested((String, String)),
59+
}
60+
5161
#[derive(Debug)]
5262
enum ActionMeta {
5363
Struct,
54-
Enum(Vec<(String, String)>),
64+
Enum(Vec<EnumElement>),
5565
}
5666

5767
impl ActionMeta {
5868
pub fn is_struct(&self) -> bool {
5969
matches!(self, Self::Struct)
6070
}
71+
72+
pub fn is_inlined(&self) -> bool {
73+
if let Self::Enum(fields) = self {
74+
fields
75+
.iter()
76+
.any(|field| matches!(field, EnumElement::InlineFields { .. }))
77+
} else {
78+
false
79+
}
80+
}
81+
82+
pub fn action_kinds(&self) -> Vec<String> {
83+
match self {
84+
Self::Struct => vec![],
85+
Self::Enum(elts) => {
86+
let mut action_kinds = elts
87+
.iter()
88+
.filter_map(|elt| match elt {
89+
EnumElement::Nested(_) => None,
90+
EnumElement::InlineFields { action_kind, .. } => Some(action_kind.clone()),
91+
})
92+
.collect::<Vec<_>>();
93+
action_kinds.sort();
94+
action_kinds
95+
}
96+
}
97+
}
6198
}
6299

63100
fn main() -> Result<(), Box<dyn Error>> {
@@ -77,8 +114,10 @@ fn main() -> Result<(), Box<dyn Error>> {
77114
};
78115

79116
let action_def_re = Regex::new(r"^pub (struct|enum) ([a-zA-Z0-9]*Action)( |\n)\{").unwrap();
80-
let action_enum_variant_re =
117+
let action_enum_variant_nested_re =
81118
Regex::new(r"([a-zA-Z0-9]*)\(\n? *([a-zA-Z0-9]*Action),?\n? *\)").unwrap();
119+
let action_enum_variant_inline_re =
120+
Regex::new(r"(?m)^\s*([A-Z][a-zA-Z0-9]+)(\s*\{[^}]*\})?,").unwrap();
82121

83122
let mut use_statements: BTreeMap<Vec<String>, Vec<String>> = Default::default();
84123
use_statements.insert(vec![], vec!["ActionKindGet".to_owned()]);
@@ -116,20 +155,45 @@ fn main() -> Result<(), Box<dyn Error>> {
116155
"enum" => {
117156
if let Some(action_name) = matches.get(2) {
118157
let action_name = action_name.as_str().to_owned();
158+
// Without 'Action' suffix
159+
let action_name_base = action_name[..(action_name.len() - 6)].to_string();
119160
let mut variant_lines = vec![];
120161
loop {
121162
let Some(line) = lines.next() else { break };
122163
let line = line.unwrap();
123-
if line.contains('}') {
164+
if line.ends_with('}') {
124165
break;
125166
}
126167
variant_lines.push(line);
127168
}
128-
let variants_str = variant_lines.join("");
169+
let variants_str = variant_lines.join("\n");
129170

130-
let variants = action_enum_variant_re
171+
let variants_nested = action_enum_variant_nested_re
172+
.captures_iter(&variants_str)
173+
.map(|matches| {
174+
EnumElement::Nested((matches[1].to_owned(), matches[2].to_owned()))
175+
})
176+
.collect::<Vec<_>>();
177+
let variants_inlined = action_enum_variant_inline_re
131178
.captures_iter(&variants_str)
132-
.map(|matches| (matches[1].to_owned(), matches[2].to_owned()))
179+
.filter_map(|matches| {
180+
let tag = matches[1].to_owned();
181+
if tag.ends_with("Action") {
182+
None
183+
} else {
184+
let action_kind = format!("{action_name_base}{tag}");
185+
Some(EnumElement::InlineFields {
186+
tag,
187+
action_kind,
188+
has_fields: matches.get(2).is_some(),
189+
})
190+
}
191+
})
192+
.collect::<Vec<_>>();
193+
let variants = variants_nested
194+
.iter()
195+
.chain(variants_inlined.iter())
196+
.cloned()
133197
.collect();
134198
actions.insert(action_name.clone(), ActionMeta::Enum(variants));
135199
action_defs.push(action_name);
@@ -198,9 +262,15 @@ fn main() -> Result<(), Box<dyn Error>> {
198262

199263
let action_kinds_iter = actions
200264
.iter()
201-
.filter(|(_, meta)| meta.is_struct())
202-
// Remove suffix `Action` from action name.
203-
.map(|(name, _)| name[..(name.len() - 6)].to_string());
265+
.filter(|(_, meta)| meta.is_struct() || meta.is_inlined())
266+
.flat_map(|(name, meta)| {
267+
if meta.is_inlined() {
268+
meta.action_kinds()
269+
} else {
270+
// Remove suffix `Action` from action name.
271+
vec![name[..(name.len() - 6)].to_string()]
272+
}
273+
});
204274
let action_kinds = std::iter::once("None".to_owned())
205275
.chain(action_kinds_iter)
206276
.collect::<Vec<_>>();
@@ -237,13 +307,33 @@ fn main() -> Result<(), Box<dyn Error>> {
237307
format!("ActionKind::{action_kind}")
238308
}
239309
ActionMeta::Enum(variants) => {
240-
for (_, a) in variants {
241-
queue.push_back(a.clone());
310+
for elt in variants {
311+
if let EnumElement::Nested((_, a)) = elt {
312+
queue.push_back(a.clone());
313+
}
242314
}
243315

244-
let variants_iter = variants
245-
.iter()
246-
.map(|(v, _)| format!(" Self::{v}(a) => a.kind(),"));
316+
let variants_iter = variants.iter().map(|elt| match elt {
317+
EnumElement::Nested((v, _)) => {
318+
format!(" Self::{v}(a) => a.kind(),")
319+
}
320+
EnumElement::InlineFields {
321+
tag,
322+
action_kind,
323+
has_fields: true,
324+
} => {
325+
format!(
326+
" Self::{tag} {{ .. }} => ActionKind::{action_kind},"
327+
)
328+
}
329+
EnumElement::InlineFields {
330+
tag,
331+
action_kind,
332+
has_fields: false,
333+
} => {
334+
format!(" Self::{tag} => ActionKind::{action_kind},")
335+
}
336+
});
247337
std::iter::once("match self {".to_owned())
248338
.chain(variants_iter)
249339
.chain(std::iter::once(" }".to_owned()))

0 commit comments

Comments
 (0)