You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
wasm-bindgen does not generate the static __wrap(ptr) method for a JavaScript class corresponding to a Rust struct if the only way instances are created is via a #[wasm_bindgen(constructor)] on the Rust side. This occurs even though the generated JavaScript class correctly manages the WASM pointer's lifetime using FinalizationRegistry and includes free() / __destroy_into_raw() methods.
The lack of __wrap seems inconsistent, as the generated JS class is fundamentally wrapping a WASM resource, regardless of whether instances are created solely via the constructor or also returned from other functions.
Steps to Reproduce
Define a Rust struct and mark it with #[wasm_bindgen]:
use wasm_bindgen::prelude::*;#[wasm_bindgen]pubstructMyThing{// internal data}#[wasm_bindgen]implMyThing{#[wasm_bindgen(constructor)]pubfnnew() -> Self{// Logic to create the thingMyThing{/* ... */}}// Add some methods that use `&self` or `&mut self`#[wasm_bindgen]pubfndo_something(&self){// ...}}// IMPORTANT: Do NOT add any other function like this:// #[wasm_bindgen]// pub fn get_a_thing() -> MyThing { /* ... */ }
Compile the Rust code to WASM and generate JavaScript bindings using wasm-bindgen.
Inspect the generated JavaScript file (e.g., my_module.js).
Observe that the MyThing class in the JavaScript file is missing the static __wrap(ptr) method, although it will have free(), __destroy_into_raw(), and the corresponding FinalizationRegistry.
Expected Behavior
The generated JavaScript MyThing class should include the static __wrap(ptr) method. Its presence indicates that the class wraps a WASM pointer, which is true even if the only creation path is the constructor. The generation of lifetime management code (FinalizationRegistry, free) further implies that __wrap should logically be present.
Actual Behavior
The generated JavaScript MyThing class lacks the static __wrap(ptr) method.
Additional Context
This issue was encountered when creating bindings for a Provider struct in a Rust library. Instances were only ever created via #[wasm_bindgen(constructor)]. Other structs in the same library, which had functions returning instances (in addition to potentially having constructors), did have the __wrap method generated correctly.
Furthermore, generating __wrap consistently is beneficial in specific environments. For instance, in Unity WebGL builds, JavaScript object references might not persist reliably across certain engine events or callbacks. A common pattern is to use __destroy_into_raw() to obtain the raw WASM pointer (which can be stored as a simple number), and later use __wrap() to reconstruct the JavaScript wrapper object when it's needed again. The absence of __wrap prevents this manual lifetime management pattern for classes that only have a #[wasm_bindgen(constructor)].
A workaround is to add a dummy #[wasm_bindgen] function to the Rust impl block that simply returns Self or a clone, for example:
#[wasm_bindgen]implMyThing{// ... other methods ...// Dummy method to force __wrap generation#[wasm_bindgen(js_name = internalGetSelf)]pubfninternal_get_self(&self) -> Self{// Return self or a clone as appropriateMyThing{/* ... */}// Or self.clone() if Clone is implemented}}
Adding this unnecessary function forces wasm-bindgen to generate the __wrap method in the JavaScript output. This suggests the generation logic for __wrap is currently tied only to non-constructor functions returning the type.
The text was updated successfully, but these errors were encountered:
Describe the Bug
wasm-bindgen
does not generate the static__wrap(ptr)
method for a JavaScript class corresponding to a Rust struct if the only way instances are created is via a#[wasm_bindgen(constructor)]
on the Rust side. This occurs even though the generated JavaScript class correctly manages the WASM pointer's lifetime usingFinalizationRegistry
and includesfree()
/__destroy_into_raw()
methods.The lack of
__wrap
seems inconsistent, as the generated JS class is fundamentally wrapping a WASM resource, regardless of whether instances are created solely via the constructor or also returned from other functions.Steps to Reproduce
#[wasm_bindgen]
:wasm-bindgen
.my_module.js
).MyThing
class in the JavaScript file is missing thestatic __wrap(ptr)
method, although it will havefree()
,__destroy_into_raw()
, and the correspondingFinalizationRegistry
.Expected Behavior
The generated JavaScript
MyThing
class should include thestatic __wrap(ptr)
method. Its presence indicates that the class wraps a WASM pointer, which is true even if the only creation path is the constructor. The generation of lifetime management code (FinalizationRegistry
,free
) further implies that__wrap
should logically be present.Actual Behavior
The generated JavaScript
MyThing
class lacks thestatic __wrap(ptr)
method.Additional Context
This issue was encountered when creating bindings for a
Provider
struct in a Rust library. Instances were only ever created via#[wasm_bindgen(constructor)]
. Other structs in the same library, which had functions returning instances (in addition to potentially having constructors), did have the__wrap
method generated correctly.Furthermore, generating
__wrap
consistently is beneficial in specific environments. For instance, in Unity WebGL builds, JavaScript object references might not persist reliably across certain engine events or callbacks. A common pattern is to use__destroy_into_raw()
to obtain the raw WASM pointer (which can be stored as a simple number), and later use__wrap()
to reconstruct the JavaScript wrapper object when it's needed again. The absence of__wrap
prevents this manual lifetime management pattern for classes that only have a#[wasm_bindgen(constructor)]
.A workaround is to add a dummy
#[wasm_bindgen]
function to the Rustimpl
block that simply returnsSelf
or a clone, for example:Adding this unnecessary function forces
wasm-bindgen
to generate the__wrap
method in the JavaScript output. This suggests the generation logic for__wrap
is currently tied only to non-constructor functions returning the type.The text was updated successfully, but these errors were encountered: