alef_codegen/conversions/
mod.rs1mod binding_to_core;
2mod core_to_binding;
3mod enums;
4pub(crate) mod helpers;
5
6use ahash::AHashSet;
7
8#[derive(Default, Clone)]
11pub struct ConversionConfig<'a> {
12 pub type_name_prefix: &'a str,
14 pub cast_large_ints_to_i64: bool,
16 pub enum_string_names: Option<&'a AHashSet<String>>,
19 pub map_uses_jsvalue: bool,
23 pub cast_f32_to_f64: bool,
25 pub optionalize_defaults: bool,
29 pub json_to_string: bool,
33 pub include_cfg_metadata: bool,
36 pub option_duration_on_defaults: bool,
42}
43
44pub use binding_to_core::{
46 field_conversion_to_core, field_conversion_to_core_cfg, gen_from_binding_to_core, gen_from_binding_to_core_cfg,
47};
48pub use core_to_binding::{
49 field_conversion_from_core, field_conversion_from_core_cfg, gen_from_core_to_binding, gen_from_core_to_binding_cfg,
50};
51pub use enums::{
52 gen_enum_from_binding_to_core, gen_enum_from_binding_to_core_cfg, gen_enum_from_core_to_binding,
53 gen_enum_from_core_to_binding_cfg,
54};
55pub use helpers::{
56 binding_to_core_match_arm, can_generate_conversion, can_generate_enum_conversion,
57 can_generate_enum_conversion_from_core, convertible_types, core_enum_path, core_to_binding_convertible_types,
58 core_to_binding_match_arm, core_type_path, has_sanitized_fields, is_tuple_variant,
59};
60
61#[cfg(test)]
62mod tests {
63 use super::*;
64 use alef_core::ir::*;
65
66 fn simple_type() -> TypeDef {
67 TypeDef {
68 name: "Config".to_string(),
69 rust_path: "my_crate::Config".to_string(),
70 fields: vec![
71 FieldDef {
72 name: "name".into(),
73 ty: TypeRef::String,
74 optional: false,
75 default: None,
76 doc: String::new(),
77 sanitized: false,
78 is_boxed: false,
79 type_rust_path: None,
80 cfg: None,
81 typed_default: None,
82 core_wrapper: CoreWrapper::None,
83 vec_inner_core_wrapper: CoreWrapper::None,
84 newtype_wrapper: None,
85 },
86 FieldDef {
87 name: "timeout".into(),
88 ty: TypeRef::Primitive(PrimitiveType::U64),
89 optional: true,
90 default: None,
91 doc: String::new(),
92 sanitized: false,
93 is_boxed: false,
94 type_rust_path: None,
95 cfg: None,
96 typed_default: None,
97 core_wrapper: CoreWrapper::None,
98 vec_inner_core_wrapper: CoreWrapper::None,
99 newtype_wrapper: None,
100 },
101 FieldDef {
102 name: "backend".into(),
103 ty: TypeRef::Named("Backend".into()),
104 optional: true,
105 default: None,
106 doc: String::new(),
107 sanitized: false,
108 is_boxed: false,
109 type_rust_path: None,
110 cfg: None,
111 typed_default: None,
112 core_wrapper: CoreWrapper::None,
113 vec_inner_core_wrapper: CoreWrapper::None,
114 newtype_wrapper: None,
115 },
116 ],
117 methods: vec![],
118 is_opaque: false,
119 is_clone: true,
120 is_trait: false,
121 has_default: false,
122 has_stripped_cfg_fields: false,
123 is_return_type: false,
124 serde_rename_all: None,
125 doc: String::new(),
126 cfg: None,
127 }
128 }
129
130 fn simple_enum() -> EnumDef {
131 EnumDef {
132 name: "Backend".to_string(),
133 rust_path: "my_crate::Backend".to_string(),
134 variants: vec![
135 EnumVariant {
136 name: "Cpu".into(),
137 fields: vec![],
138 doc: String::new(),
139 is_default: false,
140 serde_rename: None,
141 },
142 EnumVariant {
143 name: "Gpu".into(),
144 fields: vec![],
145 doc: String::new(),
146 is_default: false,
147 serde_rename: None,
148 },
149 ],
150 doc: String::new(),
151 cfg: None,
152 serde_tag: None,
153 serde_rename_all: None,
154 }
155 }
156
157 #[test]
158 fn test_from_binding_to_core() {
159 let typ = simple_type();
160 let result = gen_from_binding_to_core(&typ, "my_crate");
161 assert!(result.contains("impl From<Config> for my_crate::Config"));
162 assert!(result.contains("name: val.name"));
163 assert!(result.contains("timeout: val.timeout"));
164 assert!(result.contains("backend: val.backend.map(Into::into)"));
165 }
166
167 #[test]
168 fn test_from_core_to_binding() {
169 let typ = simple_type();
170 let result = gen_from_core_to_binding(&typ, "my_crate", &AHashSet::new());
171 assert!(result.contains("impl From<my_crate::Config> for Config"));
172 }
173
174 #[test]
175 fn test_enum_from_binding_to_core() {
176 let enum_def = simple_enum();
177 let result = gen_enum_from_binding_to_core(&enum_def, "my_crate");
178 assert!(result.contains("impl From<Backend> for my_crate::Backend"));
179 assert!(result.contains("Backend::Cpu => Self::Cpu"));
180 assert!(result.contains("Backend::Gpu => Self::Gpu"));
181 }
182
183 #[test]
184 fn test_enum_from_core_to_binding() {
185 let enum_def = simple_enum();
186 let result = gen_enum_from_core_to_binding(&enum_def, "my_crate");
187 assert!(result.contains("impl From<my_crate::Backend> for Backend"));
188 assert!(result.contains("my_crate::Backend::Cpu => Self::Cpu"));
189 assert!(result.contains("my_crate::Backend::Gpu => Self::Gpu"));
190 }
191}