refactor(napi): from_raw_unchecked and this_unchecked
This commit is contained in:
parent
d3fdfd48d0
commit
c0277542a2
10 changed files with 55 additions and 69 deletions
|
@ -93,8 +93,7 @@ pub fn js_function(attr: TokenStream, input: TokenStream) -> TokenStream {
|
||||||
use std::ffi::CString;
|
use std::ffi::CString;
|
||||||
use napi::{JsUnknown, Env, Error, Status, NapiValue, CallContext};
|
use napi::{JsUnknown, Env, Error, Status, NapiValue, CallContext};
|
||||||
let mut argc = #arg_len_span as usize;
|
let mut argc = #arg_len_span as usize;
|
||||||
let mut raw_args =
|
let mut raw_args: [napi::sys::napi_value; #arg_len_span] = [ptr::null_mut(); #arg_len_span];
|
||||||
unsafe { mem::MaybeUninit::<[napi::sys::napi_value; #arg_len_span as usize]>::uninit().assume_init() };
|
|
||||||
let mut raw_this = ptr::null_mut();
|
let mut raw_this = ptr::null_mut();
|
||||||
|
|
||||||
let mut has_error = false;
|
let mut has_error = false;
|
||||||
|
@ -112,8 +111,8 @@ pub fn js_function(attr: TokenStream, input: TokenStream) -> TokenStream {
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut env = Env::from_raw(raw_env);
|
let mut env = Env::from_raw(raw_env);
|
||||||
match CallContext::new(&mut env, cb_info, raw_this, &raw_args, #arg_len_span, argc as usize)
|
let ctx = CallContext::new(&mut env, cb_info, raw_this, &raw_args, #arg_len_span, argc as usize);
|
||||||
.and_then(|ctx| panic::catch_unwind(AssertUnwindSafe(move || #new_fn_name(ctx))).map_err(|e| {
|
match panic::catch_unwind(AssertUnwindSafe(move || #new_fn_name(ctx))).map_err(|e| {
|
||||||
let message = {
|
let message = {
|
||||||
if let Some(string) = e.downcast_ref::<String>() {
|
if let Some(string) = e.downcast_ref::<String>() {
|
||||||
string.clone()
|
string.clone()
|
||||||
|
@ -124,7 +123,7 @@ pub fn js_function(attr: TokenStream, input: TokenStream) -> TokenStream {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
Error::from_reason(message)
|
Error::from_reason(message)
|
||||||
}).and_then(|v| v))
|
}).and_then(|v| v)
|
||||||
{
|
{
|
||||||
Ok(v) => v.raw_value(),
|
Ok(v) => v.raw_value(),
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
|
|
|
@ -1,34 +1,34 @@
|
||||||
use std::ptr;
|
use std::ptr;
|
||||||
|
|
||||||
use crate::error::check_status;
|
use crate::error::check_status;
|
||||||
use crate::{sys, Either, Env, Error, JsUndefined, JsUnknown, NapiValue, Result, Status};
|
use crate::{sys, Either, Env, Error, JsUndefined, NapiValue, Result, Status};
|
||||||
|
|
||||||
pub struct CallContext<'env, T: NapiValue = JsUnknown> {
|
pub struct CallContext<'env> {
|
||||||
pub env: &'env Env,
|
pub env: &'env Env,
|
||||||
pub this: T,
|
raw_this: sys::napi_value,
|
||||||
callback_info: sys::napi_callback_info,
|
callback_info: sys::napi_callback_info,
|
||||||
args: &'env [sys::napi_value],
|
args: &'env [sys::napi_value],
|
||||||
arg_len: usize,
|
arg_len: usize,
|
||||||
actual_arg_length: usize,
|
actual_arg_length: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'env, T: NapiValue> CallContext<'env, T> {
|
impl<'env> CallContext<'env> {
|
||||||
pub fn new(
|
pub fn new(
|
||||||
env: &'env Env,
|
env: &'env Env,
|
||||||
callback_info: sys::napi_callback_info,
|
callback_info: sys::napi_callback_info,
|
||||||
this: sys::napi_value,
|
raw_this: sys::napi_value,
|
||||||
args: &'env [sys::napi_value],
|
args: &'env [sys::napi_value],
|
||||||
arg_len: usize,
|
arg_len: usize,
|
||||||
actual_arg_length: usize,
|
actual_arg_length: usize,
|
||||||
) -> Result<Self> {
|
) -> Self {
|
||||||
Ok(Self {
|
Self {
|
||||||
env,
|
env,
|
||||||
callback_info,
|
callback_info,
|
||||||
this: T::from_raw(env.0, this)?,
|
raw_this,
|
||||||
args,
|
args,
|
||||||
arg_len,
|
arg_len,
|
||||||
actual_arg_length,
|
actual_arg_length,
|
||||||
})
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get<ArgType: NapiValue>(&self, index: usize) -> Result<ArgType> {
|
pub fn get<ArgType: NapiValue>(&self, index: usize) -> Result<ArgType> {
|
||||||
|
@ -38,10 +38,7 @@ impl<'env, T: NapiValue> CallContext<'env, T> {
|
||||||
reason: "Arguments index out of range".to_owned(),
|
reason: "Arguments index out of range".to_owned(),
|
||||||
})
|
})
|
||||||
} else {
|
} else {
|
||||||
Ok(ArgType::from_raw_without_typecheck(
|
Ok(ArgType::from_raw_unchecked(self.env.0, self.args[index]))
|
||||||
self.env.0,
|
|
||||||
self.args[index],
|
|
||||||
))
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -68,4 +65,14 @@ impl<'env, T: NapiValue> CallContext<'env, T> {
|
||||||
check_status(unsafe { sys::napi_get_new_target(self.env.0, self.callback_info, &mut value) })?;
|
check_status(unsafe { sys::napi_get_new_target(self.env.0, self.callback_info, &mut value) })?;
|
||||||
V::from_raw(self.env.0, value)
|
V::from_raw(self.env.0, value)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline(always)]
|
||||||
|
pub fn this<T: NapiValue>(&self) -> Result<T> {
|
||||||
|
T::from_raw(self.env.0, self.raw_this)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline(always)]
|
||||||
|
pub fn this_unchecked<T: NapiValue>(&self) -> T {
|
||||||
|
T::from_raw_unchecked(self.env.0, self.raw_this)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -154,7 +154,7 @@ impl NapiValue for JsArrayBuffer {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fn from_raw_without_typecheck(env: sys::napi_env, value: sys::napi_value) -> Self {
|
fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> Self {
|
||||||
let mut data = ptr::null_mut();
|
let mut data = ptr::null_mut();
|
||||||
let mut len: u64 = 0;
|
let mut len: u64 = 0;
|
||||||
let status = unsafe { sys::napi_get_arraybuffer_info(env, value, &mut data, &mut len) };
|
let status = unsafe { sys::napi_get_arraybuffer_info(env, value, &mut data, &mut len) };
|
||||||
|
|
|
@ -154,7 +154,7 @@ impl NapiValue for JsBigint {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fn from_raw_without_typecheck(env: sys::napi_env, value: sys::napi_value) -> Self {
|
fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> Self {
|
||||||
let mut word_count: u64 = 0;
|
let mut word_count: u64 = 0;
|
||||||
let status = unsafe {
|
let status = unsafe {
|
||||||
sys::napi_get_value_bigint_words(
|
sys::napi_get_value_bigint_words(
|
||||||
|
|
|
@ -158,7 +158,7 @@ impl NapiValue for JsBuffer {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fn from_raw_without_typecheck(env: sys::napi_env, value: sys::napi_value) -> Self {
|
fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> Self {
|
||||||
let mut data = ptr::null_mut();
|
let mut data = ptr::null_mut();
|
||||||
let mut len: u64 = 0;
|
let mut len: u64 = 0;
|
||||||
let status = unsafe { sys::napi_get_buffer_info(env, value, &mut data, &mut len) };
|
let status = unsafe { sys::napi_get_buffer_info(env, value, &mut data, &mut len) };
|
||||||
|
|
|
@ -22,7 +22,7 @@ impl<A: NapiValue, B: NapiValue> NapiValue for Either<A, B> {
|
||||||
.or_else(|_| B::from_raw(env, value).map(Self::B))
|
.or_else(|_| B::from_raw(env, value).map(Self::B))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn from_raw_without_typecheck(env: sys::napi_env, value: sys::napi_value) -> Either<A, B> {
|
fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> Either<A, B> {
|
||||||
Self::from_raw(env, value).unwrap()
|
Self::from_raw(env, value).unwrap()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -92,7 +92,7 @@ macro_rules! impl_napi_value_trait {
|
||||||
self.0.value
|
self.0.value
|
||||||
}
|
}
|
||||||
|
|
||||||
fn from_raw_without_typecheck(env: sys::napi_env, value: sys::napi_value) -> $js_value {
|
fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> $js_value {
|
||||||
$js_value(Value {
|
$js_value(Value {
|
||||||
env,
|
env,
|
||||||
value,
|
value,
|
||||||
|
@ -101,17 +101,6 @@ macro_rules! impl_napi_value_trait {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl $js_value {
|
|
||||||
#[inline]
|
|
||||||
pub fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> Self {
|
|
||||||
Self(Value {
|
|
||||||
env,
|
|
||||||
value,
|
|
||||||
value_type: $value_type,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl TryFrom<JsUnknown> for $js_value {
|
impl TryFrom<JsUnknown> for $js_value {
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
fn try_from(value: JsUnknown) -> Result<$js_value> {
|
fn try_from(value: JsUnknown) -> Result<$js_value> {
|
||||||
|
@ -231,7 +220,7 @@ macro_rules! impl_js_value_methods {
|
||||||
pub trait NapiValue: Sized {
|
pub trait NapiValue: Sized {
|
||||||
fn from_raw(env: sys::napi_env, value: sys::napi_value) -> Result<Self>;
|
fn from_raw(env: sys::napi_env, value: sys::napi_value) -> Result<Self>;
|
||||||
|
|
||||||
fn from_raw_without_typecheck(env: sys::napi_env, value: sys::napi_value) -> Self;
|
fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> Self;
|
||||||
|
|
||||||
fn raw_value(&self) -> sys::napi_value;
|
fn raw_value(&self) -> sys::napi_value;
|
||||||
}
|
}
|
||||||
|
@ -268,7 +257,7 @@ impl NapiValue for JsUnknown {
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn from_raw_without_typecheck(env: sys::napi_env, value: sys::napi_value) -> Self {
|
fn from_raw_unchecked(env: sys::napi_env, value: sys::napi_value) -> Self {
|
||||||
JsUnknown(Value {
|
JsUnknown(Value {
|
||||||
env,
|
env,
|
||||||
value,
|
value,
|
||||||
|
|
|
@ -12,24 +12,19 @@ fn create_test_class(ctx: CallContext) -> Result<JsFunction> {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[js_function(1)]
|
#[js_function(1)]
|
||||||
fn test_class_constructor(mut ctx: CallContext<JsObject>) -> Result<JsUndefined> {
|
fn test_class_constructor(ctx: CallContext) -> Result<JsUndefined> {
|
||||||
let count = ctx.get::<JsNumber>(0)?;
|
let count = ctx.get::<JsNumber>(0)?;
|
||||||
ctx
|
let mut this: JsObject = ctx.this_unchecked();
|
||||||
.this
|
this.set_named_property("count", ctx.env.create_int32(count.try_into()?)?)?;
|
||||||
.set_named_property("count", ctx.env.create_int32(count.try_into()?)?)?;
|
|
||||||
ctx.env.get_undefined()
|
ctx.env.get_undefined()
|
||||||
}
|
}
|
||||||
|
|
||||||
#[js_function(1)]
|
#[js_function(1)]
|
||||||
fn add_count(mut ctx: CallContext<JsObject>) -> Result<JsUndefined> {
|
fn add_count(ctx: CallContext) -> Result<JsUndefined> {
|
||||||
let add: i32 = ctx.get::<JsNumber>(0)?.try_into()?;
|
let add: i32 = ctx.get::<JsNumber>(0)?.try_into()?;
|
||||||
let count: i32 = ctx
|
let mut this: JsObject = ctx.this_unchecked();
|
||||||
.this
|
let count: i32 = this.get_named_property::<JsNumber>("count")?.try_into()?;
|
||||||
.get_named_property::<JsNumber>("count")?
|
this.set_named_property("count", ctx.env.create_int32(count + add)?)?;
|
||||||
.try_into()?;
|
|
||||||
ctx
|
|
||||||
.this
|
|
||||||
.set_named_property("count", ctx.env.create_int32(count + add)?)?;
|
|
||||||
ctx.env.get_undefined()
|
ctx.env.get_undefined()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -12,11 +12,11 @@ pub fn call_function(ctx: CallContext) -> Result<JsNull> {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[js_function(1)]
|
#[js_function(1)]
|
||||||
pub fn call_function_with_this(ctx: CallContext<JsObject>) -> Result<JsNull> {
|
pub fn call_function_with_this(ctx: CallContext) -> Result<JsNull> {
|
||||||
let js_this = &ctx.this;
|
let js_this: JsObject = ctx.this_unchecked();
|
||||||
let js_func = ctx.get::<JsFunction>(0)?;
|
let js_func = ctx.get::<JsFunction>(0)?;
|
||||||
|
|
||||||
js_func.call(Some(js_this), &[])?;
|
js_func.call(Some(&js_this), &[])?;
|
||||||
|
|
||||||
ctx.env.get_null()
|
ctx.env.get_null()
|
||||||
}
|
}
|
||||||
|
|
|
@ -139,15 +139,11 @@ fn test_define_properties(ctx: CallContext) -> Result<JsUndefined> {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[js_function(1)]
|
#[js_function(1)]
|
||||||
fn add(mut ctx: CallContext<JsObject>) -> Result<JsUndefined> {
|
fn add(ctx: CallContext) -> Result<JsUndefined> {
|
||||||
let count: i32 = ctx
|
let mut this: JsObject = ctx.this_unchecked();
|
||||||
.this
|
let count: i32 = this.get_named_property::<JsNumber>("count")?.try_into()?;
|
||||||
.get_named_property::<JsNumber>("count")?
|
|
||||||
.try_into()?;
|
|
||||||
let value_to_add: i32 = ctx.get::<JsNumber>(0)?.try_into()?;
|
let value_to_add: i32 = ctx.get::<JsNumber>(0)?.try_into()?;
|
||||||
ctx
|
this.set_named_property("count", ctx.env.create_int32(count + value_to_add)?)?;
|
||||||
.this
|
|
||||||
.set_named_property("count", ctx.env.create_int32(count + value_to_add)?)?;
|
|
||||||
ctx.env.get_undefined()
|
ctx.env.get_undefined()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue