-
Notifications
You must be signed in to change notification settings - Fork 9
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
RFC: add pyo3-like attribute macros to define nodejs classes and methods #43
base: main
Are you sure you want to change the base?
Changes from 1 commit
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,75 @@ | ||
- Feature Name: adding_pyo3_like_attribute_macros_for_classes_and_methods | ||
- Start Date: 2021-06-02 | ||
- RFC PR: (leave this empty) | ||
- Neon Issue: (leave this empty) | ||
|
||
# Summary | ||
[summary]: #summary | ||
|
||
This RFC proposes adding [PyO3-like](https://pyo3.rs/v0.13.2/class.html) attribute-macros to define JavaScript classes as Rust structs. | ||
|
||
# Motivation | ||
[motivation]: #motivation | ||
|
||
At the moment of migration to `napi`, there is no idiomatic way of writing JavaScript classes in pure Rust. This proposal adds the attribute macros to help users to write classes and methods easily. | ||
|
||
# Guide-level explanation | ||
[guide-level-explanation]: #guide-level-explanation | ||
|
||
I will describe some potential use cases here: | ||
```rust | ||
#[neon::class] | ||
struct Person { | ||
name: string, | ||
age: u8, | ||
} | ||
#[neon::methods] | ||
impl Person { | ||
fn greet(&self, cx: FunctionContext) -> JsResult<JsString> { | ||
Ok(cx.string(format!("Hello, my name is {}", self.name))) | ||
} | ||
|
||
#[neon::constructor] | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The current
I think this is valuable and it would be nice to maintain that functionality. I can think of a couple ways to implement it:
create_class(Person { name, age }) |
||
fn new(mut cx: FunctionContext) -> Self { | ||
let name = cx.argument::<JsString>(0)?.value(&mut cx); | ||
let age = cx.argument::<JsNumber>(1)?.value(&mut cx); | ||
Person { name, age } | ||
} | ||
} | ||
``` | ||
|
||
Then we can use `Person` class as the following | ||
```JavaScript | ||
let p = Person("Peter", 25); | ||
p.greet(); // Hello, my name is Peter | ||
``` | ||
|
||
# Reference-level explanation | ||
[reference-level-explanation]: #reference-level-explanation | ||
|
||
This is the technical portion of the RFC. Explain the design in sufficient detail that: | ||
|
||
- Its interaction with other features is clear. | ||
- It is reasonably clear how the feature would be implemented. | ||
- Corner cases are dissected by example. | ||
|
||
This section should return to the examples given in the previous section, and explain more fully how the detailed proposal makes those examples work. | ||
|
||
# Drawbacks | ||
[drawbacks]: #drawbacks | ||
|
||
Why should we _not_ do this? | ||
|
||
# Rationale and alternatives | ||
[alternatives]: #alternatives | ||
|
||
- Why is this design the best in the space of possible designs? | ||
- What other designs have been considered and what is the rationale for not choosing them? | ||
- What is the impact of not doing this? | ||
|
||
# Unresolved questions | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Some unresolved questions that I have.
|
||
[unresolved]: #unresolved-questions | ||
|
||
- What parts of the design do you expect to resolve through the RFC process before this gets merged? | ||
- What parts of the design do you expect to resolve through the implementation of this feature before stabilization? | ||
- What related issues do you consider out of scope for this RFC that could be addressed in the future independently of the solution that comes out of this RFC? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think these should be namespaced to help prevent conflicts with other macros. This could be named
neon::class_methods
or we could have everything in aneon::class
module.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Currently neon only has one proc/attribute macro, right?
main
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That's correct.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I actually prefer the simplicity of
#[neon::methods], #[neon::classes]
if in a foreseeable future there won't be any namespace conflicts.