de.rs
1 use napi::{ 2 Env, JsString, JsValue, Unknown, ValueType, 3 bindgen_prelude::{BigInt, FromNapiValue, JsObjectValue, Object, Uint8Array}, 4 }; 5 use serde_core::{ 6 de::{DeserializeSeed, Error, IntoDeserializer, MapAccess, SeqAccess}, 7 forward_to_deserialize_any, 8 }; 9 10 pub(crate) struct DuperMetaDeserializer<'env> { 11 pub(crate) env: &'env Env, 12 pub(crate) object: Object<'env>, 13 } 14 15 impl<'de, 'env> serde_core::Deserializer<'de> for DuperMetaDeserializer<'env> { 16 type Error = serde_core::de::value::Error; 17 18 fn is_human_readable(&self) -> bool { 19 true 20 } 21 22 fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Self::Error> 23 where 24 V: serde_core::de::Visitor<'de>, 25 { 26 self.deserialize_map(visitor) 27 } 28 29 fn deserialize_map<V>(self, visitor: V) -> Result<V::Value, Self::Error> 30 where 31 V: serde_core::de::Visitor<'de>, 32 { 33 let keys = self.object.get_property_names().map_err(|err| { 34 serde_core::de::value::Error::custom(format!("failed to get property names: {err}")) 35 })?; 36 let array_length = keys.get_array_length().expect("checked array creation"); 37 visitor.visit_map(DuperMetaMapAccess { 38 env: self.env, 39 object: self.object, 40 keys, 41 array_length, 42 curr_value: None, 43 i: 0, 44 }) 45 } 46 47 forward_to_deserialize_any! { 48 bool i8 i16 i32 i64 i128 u8 u16 u32 u64 u128 f32 f64 char 49 str string bytes byte_buf identifier ignored_any struct 50 option unit unit_struct newtype_struct seq tuple tuple_struct enum 51 } 52 } 53 54 struct DuperMetaMapAccess<'env> { 55 env: &'env Env, 56 object: Object<'env>, 57 keys: Object<'env>, 58 curr_value: Option<Unknown<'env>>, 59 array_length: u32, 60 i: u32, 61 } 62 63 impl<'de, 'env> MapAccess<'de> for DuperMetaMapAccess<'env> { 64 type Error = serde_core::de::value::Error; 65 66 fn size_hint(&self) -> Option<usize> { 67 Some((self.array_length - self.i) as usize) 68 } 69 70 fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>, Self::Error> 71 where 72 K: DeserializeSeed<'de>, 73 { 74 if self.i < self.array_length { 75 let key: String = self.keys.get_element(self.i).map_err(|err| { 76 serde_core::de::value::Error::custom(format!( 77 "error accessing index {} of object keys: {err:?}", 78 self.i 79 )) 80 })?; 81 self.curr_value = Some( 82 self.object 83 .get_property::<JsString, Unknown>( 84 self.env 85 .create_string(key.as_str()) 86 .expect("checked string"), 87 ) 88 .map_err(|err| { 89 serde_core::de::value::Error::custom(format!( 90 "error accessing property {} of object: {err:?}", 91 &key 92 )) 93 })?, 94 ); 95 self.i += 1; 96 seed.deserialize(key.into_deserializer()).map(Some) 97 } else { 98 Ok(None) 99 } 100 } 101 102 fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value, Self::Error> 103 where 104 V: DeserializeSeed<'de>, 105 { 106 if let Some(value) = self.curr_value.take() { 107 match value.get_type() { 108 Ok(ValueType::Undefined) | Ok(ValueType::Null) => { 109 seed.deserialize(DuperMetaInnerNull) 110 } 111 Ok(ValueType::Boolean) => seed.deserialize( 112 value 113 .coerce_to_bool() 114 .expect("checked bool") 115 .into_deserializer(), 116 ), 117 Ok(ValueType::Number) => seed.deserialize( 118 value 119 .coerce_to_number() 120 .expect("checked number") 121 .get_double() 122 .expect("infallible conversion to f64") 123 .into_deserializer(), 124 ), 125 Ok(ValueType::String) => seed.deserialize( 126 value 127 .coerce_to_string() 128 .expect("checked string") 129 .into_utf8() 130 .expect("valid UTF-8") 131 .as_str() 132 .expect("valid conversion to &str") 133 .into_deserializer(), 134 ), 135 Ok(ValueType::BigInt) => seed.deserialize( 136 BigInt::from_unknown(value) 137 .expect("checked bigint") 138 .get_i64() 139 .0 140 .into_deserializer(), 141 ), 142 Ok(ValueType::Object) => { 143 if value.is_array().expect("array type check") { 144 seed.deserialize(DuperMetaInnerArrayDeserializer { 145 env: self.env, 146 array: value.coerce_to_object().expect("checked object"), 147 }) 148 } else if let Ok(bytes) = Uint8Array::from_unknown(value) { 149 seed.deserialize(bytes.as_ref().into_deserializer()) 150 } else { 151 seed.deserialize(DuperMetaInnerObjectDeserializer { 152 env: self.env, 153 object: value.coerce_to_object().expect("checked object"), 154 }) 155 } 156 } 157 Ok(_) | Err(_) => Err(serde_core::de::value::Error::custom("unknown value type")), 158 } 159 } else { 160 Err(serde_core::de::value::Error::custom("missing value")) 161 } 162 } 163 } 164 165 pub(crate) struct DuperMetaInnerObjectDeserializer<'env> { 166 pub(crate) env: &'env Env, 167 pub(crate) object: Object<'env>, 168 } 169 170 impl<'de, 'env> serde_core::Deserializer<'de> for DuperMetaInnerObjectDeserializer<'env> { 171 type Error = serde_core::de::value::Error; 172 173 fn is_human_readable(&self) -> bool { 174 true 175 } 176 177 fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Self::Error> 178 where 179 V: serde_core::de::Visitor<'de>, 180 { 181 self.deserialize_map(visitor) 182 } 183 184 fn deserialize_map<V>(self, visitor: V) -> Result<V::Value, Self::Error> 185 where 186 V: serde_core::de::Visitor<'de>, 187 { 188 let keys = self.object.get_property_names().map_err(|err| { 189 serde_core::de::value::Error::custom(format!("failed to get property names: {err}")) 190 })?; 191 let array_length = keys.get_array_length().expect("checked array creation"); 192 visitor.visit_map(DuperMetaInnerObjectMapAccess { 193 env: self.env, 194 object: self.object, 195 keys, 196 array_length, 197 curr_value: None, 198 i: 0, 199 }) 200 } 201 202 forward_to_deserialize_any! { 203 bool i8 i16 i32 i64 i128 u8 u16 u32 u64 u128 f32 f64 char 204 str string bytes byte_buf identifier ignored_any struct 205 option unit unit_struct newtype_struct seq tuple tuple_struct enum 206 } 207 } 208 209 struct DuperMetaInnerObjectMapAccess<'env> { 210 env: &'env Env, 211 object: Object<'env>, 212 keys: Object<'env>, 213 curr_value: Option<Unknown<'env>>, 214 array_length: u32, 215 i: u32, 216 } 217 218 impl<'de, 'env> MapAccess<'de> for DuperMetaInnerObjectMapAccess<'env> { 219 type Error = serde_core::de::value::Error; 220 221 fn size_hint(&self) -> Option<usize> { 222 Some((self.array_length - self.i) as usize) 223 } 224 225 fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>, Self::Error> 226 where 227 K: DeserializeSeed<'de>, 228 { 229 if self.i < self.array_length { 230 let key: String = self.keys.get_element(self.i).map_err(|err| { 231 serde_core::de::value::Error::custom(format!( 232 "error accessing index {} of object keys: {err:?}", 233 self.i 234 )) 235 })?; 236 self.curr_value = Some( 237 self.object 238 .get_property::<JsString, Unknown>( 239 self.env.create_string(key.as_str()).map_err(|err| { 240 serde_core::de::value::Error::custom(format!( 241 "error converting property {} to string: {err:?}", 242 &key 243 )) 244 })?, 245 ) 246 .map_err(|err| { 247 serde_core::de::value::Error::custom(format!( 248 "error accessing property {} of object: {err:?}", 249 &key 250 )) 251 })?, 252 ); 253 self.i += 1; 254 seed.deserialize(key.into_deserializer()).map(Some) 255 } else { 256 Ok(None) 257 } 258 } 259 260 fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value, Self::Error> 261 where 262 V: DeserializeSeed<'de>, 263 { 264 if let Some(value) = self.curr_value.take() { 265 seed.deserialize(DuperMetaDeserializer { 266 env: self.env, 267 object: value.coerce_to_object().map_err(|err| { 268 serde_core::de::value::Error::custom(format!( 269 "error converting map value to object: {err:?}", 270 )) 271 })?, 272 }) 273 } else { 274 Err(serde_core::de::value::Error::custom("missing value")) 275 } 276 } 277 } 278 279 pub(crate) struct DuperMetaInnerArrayDeserializer<'env> { 280 pub(crate) env: &'env Env, 281 pub(crate) array: Object<'env>, 282 } 283 284 impl<'de, 'env> serde_core::Deserializer<'de> for DuperMetaInnerArrayDeserializer<'env> { 285 type Error = serde_core::de::value::Error; 286 287 fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Self::Error> 288 where 289 V: serde_core::de::Visitor<'de>, 290 { 291 self.deserialize_seq(visitor) 292 } 293 294 fn deserialize_seq<V>(self, visitor: V) -> Result<V::Value, Self::Error> 295 where 296 V: serde_core::de::Visitor<'de>, 297 { 298 let array_length = self.array.get_array_length().expect("checked array"); 299 visitor.visit_seq(DuperMetaInnerArraySeqAccess { 300 env: self.env, 301 array: self.array, 302 array_length, 303 i: 0, 304 }) 305 } 306 307 forward_to_deserialize_any! { 308 bool i8 i16 i32 i64 i128 u8 u16 u32 u64 u128 f32 f64 char 309 str string bytes byte_buf identifier ignored_any map struct 310 option unit unit_struct newtype_struct tuple tuple_struct enum 311 } 312 } 313 314 struct DuperMetaInnerArraySeqAccess<'env> { 315 env: &'env Env, 316 array: Object<'env>, 317 array_length: u32, 318 i: u32, 319 } 320 321 impl<'de, 'env> SeqAccess<'de> for DuperMetaInnerArraySeqAccess<'env> { 322 type Error = serde_core::de::value::Error; 323 324 fn size_hint(&self) -> Option<usize> { 325 Some((self.array_length - self.i) as usize) 326 } 327 328 fn next_element_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>, Self::Error> 329 where 330 T: DeserializeSeed<'de>, 331 { 332 if self.i < self.array_length { 333 let object = self.array.get_element::<Object>(self.i).map_err(|err| { 334 serde_core::de::value::Error::custom(format!( 335 "failed to get object from array: {err}" 336 )) 337 })?; 338 self.i += 1; 339 Ok(Some(seed.deserialize(DuperMetaDeserializer { 340 env: self.env, 341 object, 342 })?)) 343 } else { 344 Ok(None) 345 } 346 } 347 } 348 349 struct DuperMetaInnerNull; 350 351 impl<'de> serde_core::Deserializer<'de> for DuperMetaInnerNull { 352 type Error = serde_core::de::value::Error; 353 354 fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Self::Error> 355 where 356 V: serde_core::de::Visitor<'de>, 357 { 358 visitor.visit_none() 359 } 360 361 forward_to_deserialize_any! { 362 bool i8 i16 i32 i64 i128 u8 u16 u32 u64 u128 f32 f64 char 363 str string bytes byte_buf identifier ignored_any map struct 364 option unit unit_struct newtype_struct seq tuple tuple_struct enum 365 } 366 }