Skip to content

Commit 9bc92b6

Browse files
committed
fix: Add logic to remove default parameters from generics for fix #67
1 parent fbb5a15 commit 9bc92b6

File tree

3 files changed

+117
-4
lines changed

3 files changed

+117
-4
lines changed

tests/generics.rs

Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
use indoc::indoc;
44
use pretty_assertions::assert_eq;
5+
use serde::{Deserialize, Serialize};
56
use tsify::Tsify;
67

78
#[test]
@@ -140,3 +141,92 @@ fn test_generic_enum_with_namespace() {
140141

141142
assert_eq!(GenericEnum::<(), ()>::DECL, expected);
142143
}
144+
145+
#[test]
146+
fn test_generics_with_default_params() {
147+
#[derive(Serialize, Tsify)]
148+
#[tsify(into_wasm_abi)]
149+
struct SerNamedTuple<A = i32, B = String, C = ()>(A, B, C);
150+
151+
let expected = indoc! {r#"
152+
export type SerNamedTuple<A, B, C> = [A, B, C];"#
153+
};
154+
155+
assert_eq!(SerNamedTuple::<(), (), ()>::DECL, expected);
156+
157+
#[derive(Deserialize, Tsify)]
158+
#[tsify(from_wasm_abi)]
159+
struct DeNamedTuple<A = i32, B = String, C = ()>(A, B, C);
160+
161+
let expected = indoc! {r#"
162+
export type SerNamedTuple<A, B, C> = [A, B, C];"#
163+
};
164+
165+
assert_eq!(SerNamedTuple::<(), (), ()>::DECL, expected);
166+
167+
#[derive(Serialize, Tsify)]
168+
#[tsify(into_wasm_abi)]
169+
struct SerNamedMap<A, B = (), C = i32> {
170+
a: A,
171+
b: B,
172+
c: C,
173+
}
174+
175+
let expected = indoc! {r#"
176+
export interface SerNamedMap<A, B, C> {
177+
a: A;
178+
b: B;
179+
c: C;
180+
}"#
181+
};
182+
183+
assert_eq!(SerNamedMap::<(), (), ()>::DECL, expected);
184+
185+
#[derive(Deserialize, Tsify)]
186+
#[tsify(from_wasm_abi)]
187+
struct DeNamedMap<A, B = (), C = i32> {
188+
a: A,
189+
b: B,
190+
c: C,
191+
}
192+
193+
let expected = indoc! {r#"
194+
export interface DeNamedMap<A, B, C> {
195+
a: A;
196+
b: B;
197+
c: C;
198+
}"#
199+
};
200+
201+
assert_eq!(DeNamedMap::<(), (), ()>::DECL, expected);
202+
203+
#[derive(Serialize, Tsify)]
204+
#[tsify(into_wasm_abi)]
205+
enum SerEnum<A, B = (), C = i32> {
206+
Unit,
207+
NewType(A),
208+
Seq(i8, B),
209+
Map { a: i8, b: B, c: C },
210+
}
211+
212+
let expected = indoc! {r#"
213+
export type SerEnum<A, B, C> = "Unit" | { NewType: A } | { Seq: [number, B] } | { Map: { a: number; b: B; c: C } };"#
214+
};
215+
216+
assert_eq!(SerEnum::<(), (), ()>::DECL, expected);
217+
218+
#[derive(Deserialize, Tsify)]
219+
#[tsify(from_wasm_abi)]
220+
enum DeEnum<A, B = (), C = i32> {
221+
Unit,
222+
NewType(A),
223+
Seq(i8, B),
224+
Map { a: i8, b: B, c: C },
225+
}
226+
227+
let expected = indoc! {r#"
228+
export type DeEnum<A, B, C> = "Unit" | { NewType: A } | { Seq: [number, B] } | { Map: { a: number; b: B; c: C } };"#
229+
};
230+
231+
assert_eq!(DeEnum::<(), (), ()>::DECL, expected);
232+
}

tsify-macros/src/container.rs

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,28 @@ impl<'a> Container<'a> {
9292
self.serde_container.generics
9393
}
9494

95+
/// Remove the default from every type parameter because in the generated impls
96+
/// they look like associated types: "error: associated type bindings are not
97+
/// allowed here".
98+
pub fn generics_without_defaults(&self) -> syn::Generics {
99+
let generics = self.generics();
100+
syn::Generics {
101+
params: generics
102+
.params
103+
.iter()
104+
.map(|param| match param {
105+
syn::GenericParam::Type(param) => syn::GenericParam::Type(syn::TypeParam {
106+
eq_token: None,
107+
default: None,
108+
..param.clone()
109+
}),
110+
_ => param.clone(),
111+
})
112+
.collect(),
113+
..generics.clone()
114+
}
115+
}
116+
95117
/// Information about the data fields of the type as parsed by Serde.
96118
pub fn serde_data(&self) -> &ast::Data<'_> {
97119
&self.serde_container.data

tsify-macros/src/wasm_bindgen.rs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,8 @@ pub fn expand(cont: &Container, decl: Decl) -> TokenStream {
99
let ident = cont.ident();
1010

1111
let decl_str = decl.to_string();
12-
let (impl_generics, ty_generics, where_clause) = cont.generics().split_for_impl();
12+
let generics = cont.generics_without_defaults();
13+
let (impl_generics, ty_generics, where_clause) = generics.split_for_impl();
1314

1415
let typescript_custom_section = quote! {
1516
#[wasm_bindgen(typescript_custom_section)]
@@ -95,9 +96,9 @@ pub fn expand(cont: &Container, decl: Decl) -> TokenStream {
9596
fn expand_into_wasm_abi(cont: &Container) -> TokenStream {
9697
let ident = cont.ident();
9798
let serde_path = cont.serde_container.attrs.serde_path();
99+
let mut generics = cont.generics_without_defaults();
100+
let borrowed_generics = generics.clone();
98101

99-
let borrowed_generics = cont.generics();
100-
let mut generics = cont.generics().clone();
101102
generics
102103
.make_where_clause()
103104
.predicates
@@ -202,7 +203,7 @@ fn expand_from_wasm_abi(cont: &Container) -> TokenStream {
202203
let ident = cont.ident();
203204
let serde_path = cont.serde_container.attrs.serde_path();
204205

205-
let mut generics = cont.generics().clone();
206+
let mut generics = cont.generics_without_defaults();
206207

207208
generics
208209
.make_where_clause()

0 commit comments

Comments
 (0)