napi/bindgen_runtime/js_values/
symbol.rs

1use std::ptr;
2
3use crate::{
4  bindgen_runtime::{Env, FromNapiValue, Result, ToNapiValue, TypeName, ValidateNapiValue},
5  check_status, sys, JsSymbol,
6};
7
8pub struct Symbol {
9  desc: Option<String>,
10  #[cfg(feature = "napi9")]
11  for_desc: Option<String>,
12}
13
14impl TypeName for Symbol {
15  fn type_name() -> &'static str {
16    "Symbol"
17  }
18
19  fn value_type() -> crate::ValueType {
20    crate::ValueType::Symbol
21  }
22}
23
24impl ValidateNapiValue for Symbol {}
25
26impl Symbol {
27  pub fn new<S: ToString>(desc: S) -> Self {
28    Self {
29      desc: Some(desc.to_string()),
30      #[cfg(feature = "napi9")]
31      for_desc: None,
32    }
33  }
34
35  pub fn identity() -> Self {
36    Self {
37      desc: None,
38      #[cfg(feature = "napi9")]
39      for_desc: None,
40    }
41  }
42
43  #[cfg(feature = "napi9")]
44  pub fn for_desc<S: AsRef<str>>(desc: S) -> Self {
45    Self {
46      desc: None,
47      for_desc: Some(desc.as_ref().to_owned()),
48    }
49  }
50
51  /// Convert `Symbol` to `JsSymbol`
52  pub fn into_js_symbol<'env>(self, env: &'env Env) -> Result<JsSymbol<'env>> {
53    let napi_value = unsafe { ToNapiValue::to_napi_value(env.0, self)? };
54    unsafe { JsSymbol::from_napi_value(env.0, napi_value) }
55  }
56}
57
58impl ToNapiValue for Symbol {
59  unsafe fn to_napi_value(env: sys::napi_env, val: Self) -> crate::Result<sys::napi_value> {
60    let mut symbol_value = ptr::null_mut();
61    #[cfg(feature = "napi9")]
62    if let Some(desc) = val.for_desc {
63      check_status!(
64        unsafe {
65          sys::node_api_symbol_for(
66            env,
67            desc.as_ptr().cast(),
68            desc.len() as isize,
69            &mut symbol_value,
70          )
71        },
72        "Failed to call node_api_symbol_for"
73      )?;
74      return Ok(symbol_value);
75    }
76    check_status!(unsafe {
77      sys::napi_create_symbol(
78        env,
79        match val.desc {
80          Some(desc) => {
81            let mut desc_string = ptr::null_mut();
82            let desc_len = desc.len();
83            check_status!(sys::napi_create_string_utf8(
84              env,
85              desc.as_ptr().cast(),
86              desc_len as isize,
87              &mut desc_string
88            ))?;
89            desc_string
90          }
91          None => ptr::null_mut(),
92        },
93        &mut symbol_value,
94      )
95    })?;
96    Ok(symbol_value)
97  }
98}
99
100impl FromNapiValue for Symbol {
101  unsafe fn from_napi_value(
102    _env: sys::napi_env,
103    _napi_val: sys::napi_value,
104  ) -> crate::Result<Self> {
105    Ok(Self {
106      desc: None,
107      #[cfg(feature = "napi9")]
108      for_desc: None,
109    })
110  }
111}