neon-bindings / examples

A collection of examples of Neon
324 stars 43 forks source link

Request: Example of database connection in Rust #66

Closed vtenfys closed 3 years ago

vtenfys commented 3 years ago

I'd like to request an example with the following characteristics:

I've tried to create a simple example of this myself but haven't had success - I'm not sure if it can be achieved with classes or if it needs use of JsBox from the N-API, but based on the docs, but it seems like Rust structs can't be mutated once boxed / once encapsulated in a class. Presumably there's a way of doing this that I'm unaware of?

vtenfys commented 3 years ago

Aha, looking at this test I can see that it can be achieved with the N-API - I'll have another go at creating this example myself now that I can see it can be done :)

kjvalencik commented 3 years ago

The JsBox design only allows immutable pointers because pointers can be arbitrarily aliased in JavaScript. In order to maintain Rust's semantics for mutability, Neon only gives immutable reference because we cannot statically prove that a reference isn't shared.

However, the "fix" for this is exactly the same as any other Rust code that requires mutability from a shared reference: interior mutability.

https://doc.rust-lang.org/book/ch15-05-interior-mutability.html https://doc.rust-lang.org/std/cell/ https://doc.rust-lang.org/std/sync/

One thing we can prove at runtime is that there is only a single thread of execution while the VM is locked (a Context exists). This means it's not necessary to use a Mutex, instead a more simple RefCell can be used. Code that uses a RefCell will be panic free as long as the caller doesn't send the same Rust value in twice while also accessing the interior value.

FYI, the same can be achieved with the legacy backend and classes; however, there is a buggy implementation for runtime reference checking that allows for undefined behavior.

kjvalencik commented 3 years ago

FYI, I closed this issue because the requested example is effectively the same as the example provided for JsBox: https://docs.rs/neon/0.7.1-napi/neon/types/struct.JsBox.html#examples

It only differs in the type it is holding.