Skip to main content

ryo_mutations/basic/
enum_def.rs

1//! Enum mutations: AddEnumMutation, RemoveEnumMutation, AddVariantMutation, RemoveVariantMutation
2
3use ryo_source::pure::{PureField, PureFields, PureType, PureVis};
4use ryo_symbol::SymbolId;
5
6use crate::Mutation;
7
8/// Add a new enum to the file
9#[derive(Debug, Clone)]
10pub struct AddEnumMutation {
11    /// Parent module SymbolId
12    pub parent: SymbolId,
13    pub name: String,
14    pub variants: Vec<(String, PureFields)>, // (variant_name, fields)
15    pub is_pub: bool,
16    pub derives: Vec<String>,
17}
18
19impl AddEnumMutation {
20    pub fn new(parent: SymbolId, name: impl Into<String>) -> Self {
21        Self {
22            parent,
23            name: name.into(),
24            variants: Vec::new(),
25            is_pub: false,
26            derives: Vec::new(),
27        }
28    }
29
30    pub fn with_variant(mut self, name: impl Into<String>) -> Self {
31        self.variants.push((name.into(), PureFields::Unit));
32        self
33    }
34
35    pub fn with_tuple_variant(mut self, name: impl Into<String>, types: Vec<String>) -> Self {
36        let fields: Vec<PureType> = types.into_iter().map(PureType::Path).collect();
37        self.variants.push((name.into(), PureFields::Tuple(fields)));
38        self
39    }
40
41    pub fn with_struct_variant(
42        mut self,
43        name: impl Into<String>,
44        fields: Vec<(String, String)>,
45    ) -> Self {
46        let pure_fields: Vec<PureField> = fields
47            .into_iter()
48            .map(|(n, t)| PureField {
49                attrs: Vec::new(),
50                vis: PureVis::Private,
51                name: n,
52                ty: PureType::Path(t),
53            })
54            .collect();
55        self.variants
56            .push((name.into(), PureFields::Named(pure_fields)));
57        self
58    }
59
60    pub fn public(mut self) -> Self {
61        self.is_pub = true;
62        self
63    }
64
65    pub fn with_derives(mut self, derives: Vec<String>) -> Self {
66        self.derives = derives;
67        self
68    }
69}
70
71impl Mutation for AddEnumMutation {
72    fn describe(&self) -> String {
73        let vis = if self.is_pub { "pub " } else { "" };
74        format!(
75            "Add {}enum {} with {} variants to {}",
76            vis,
77            self.name,
78            self.variants.len(),
79            self.parent
80        )
81    }
82
83    fn mutation_type(&self) -> &'static str {
84        "AddEnum"
85    }
86
87    fn box_clone(&self) -> Box<dyn Mutation> {
88        Box::new(self.clone())
89    }
90}
91
92/// Remove an enum from the file
93#[derive(Debug, Clone)]
94pub struct RemoveEnumMutation {
95    pub symbol_id: SymbolId,
96}
97
98impl RemoveEnumMutation {
99    pub fn new(symbol_id: SymbolId) -> Self {
100        Self { symbol_id }
101    }
102}
103
104impl Mutation for RemoveEnumMutation {
105    fn describe(&self) -> String {
106        format!("Remove enum {}", self.symbol_id)
107    }
108
109    fn mutation_type(&self) -> &'static str {
110        "RemoveEnum"
111    }
112
113    fn box_clone(&self) -> Box<dyn Mutation> {
114        Box::new(self.clone())
115    }
116}
117
118/// Add a variant to an existing enum
119#[derive(Debug, Clone)]
120pub struct AddVariantMutation {
121    pub enum_id: SymbolId,
122    pub variant_name: String,
123    pub fields: PureFields,
124}
125
126impl AddVariantMutation {
127    pub fn new(enum_id: SymbolId, variant_name: impl Into<String>, fields: PureFields) -> Self {
128        Self {
129            enum_id,
130            variant_name: variant_name.into(),
131            fields,
132        }
133    }
134
135    pub fn unit(enum_id: SymbolId, variant_name: impl Into<String>) -> Self {
136        Self::new(enum_id, variant_name, PureFields::Unit)
137    }
138
139    pub fn tuple(enum_id: SymbolId, variant_name: impl Into<String>, types: Vec<String>) -> Self {
140        Self::new(
141            enum_id,
142            variant_name,
143            PureFields::Tuple(types.into_iter().map(PureType::Path).collect()),
144        )
145    }
146
147    pub fn struct_variant(
148        enum_id: SymbolId,
149        variant_name: impl Into<String>,
150        fields: Vec<(String, String)>,
151    ) -> Self {
152        let pure_fields: Vec<PureField> = fields
153            .into_iter()
154            .map(|(n, t)| PureField {
155                attrs: Vec::new(),
156                vis: PureVis::Private,
157                name: n,
158                ty: PureType::Path(t),
159            })
160            .collect();
161        Self::new(enum_id, variant_name, PureFields::Named(pure_fields))
162    }
163}
164
165impl Mutation for AddVariantMutation {
166    fn describe(&self) -> String {
167        format!("Add variant {} to enum {}", self.variant_name, self.enum_id)
168    }
169
170    fn mutation_type(&self) -> &'static str {
171        "AddVariant"
172    }
173
174    fn box_clone(&self) -> Box<dyn Mutation> {
175        Box::new(self.clone())
176    }
177}
178
179/// Remove a variant from an enum
180#[derive(Debug, Clone)]
181pub struct RemoveVariantMutation {
182    /// Pre-resolved SymbolId for the target enum (required - O(1) access)
183    pub enum_id: SymbolId,
184    pub variant_name: String,
185}
186
187impl RemoveVariantMutation {
188    pub fn new(enum_id: SymbolId, variant_name: impl Into<String>) -> Self {
189        Self {
190            enum_id,
191            variant_name: variant_name.into(),
192        }
193    }
194}
195
196impl Mutation for RemoveVariantMutation {
197    fn describe(&self) -> String {
198        format!(
199            "Remove variant {} from enum {}",
200            self.variant_name, self.enum_id
201        )
202    }
203
204    fn mutation_type(&self) -> &'static str {
205        "RemoveVariant"
206    }
207
208    fn box_clone(&self) -> Box<dyn Mutation> {
209        Box::new(self.clone())
210    }
211}