1use core::marker::PhantomData;
2
3use near_sdk::{
4 serde::{Deserialize, Deserializer, Serialize, Serializer, de},
5 serde_with::{DeserializeAs, SerializeAs},
6};
7
8use crate::TypedCurve;
9
10pub struct AsCurve<C: TypedCurve>(PhantomData<C>);
11
12impl<C: TypedCurve, const N: usize> SerializeAs<[u8; N]> for AsCurve<C> {
13 fn serialize_as<S>(source: &[u8; N], serializer: S) -> Result<S::Ok, S::Error>
14 where
15 S: Serializer,
16 {
17 C::to_base58(source).serialize(serializer)
18 }
19}
20
21impl<'de, C: TypedCurve, const N: usize> DeserializeAs<'de, [u8; N]> for AsCurve<C> {
22 fn deserialize_as<D>(deserializer: D) -> Result<[u8; N], D::Error>
23 where
24 D: Deserializer<'de>,
25 {
26 let s = <&str as Deserialize>::deserialize(deserializer)?;
27 C::parse_base58(s).map_err(de::Error::custom)
28 }
29}
30
31#[cfg(feature = "abi")]
32const _: () = {
33 use near_sdk::{
34 schemars::{
35 JsonSchema,
36 r#gen::SchemaGenerator,
37 schema::{InstanceType, Schema, SchemaObject, StringValidation},
38 },
39 serde_with::schemars_0_8::JsonSchemaAs,
40 };
41
42 impl<C: TypedCurve, const N: usize> JsonSchemaAs<[u8; N]> for AsCurve<C> {
43 fn schema_name() -> String {
44 String::schema_name()
45 }
46
47 fn json_schema(_gen: &mut SchemaGenerator) -> Schema {
48 SchemaObject {
49 instance_type: Some(InstanceType::String.into()),
50 string: Some(
51 StringValidation {
52 pattern: Some(format!("^{}:", C::CURVE_TYPE)),
53 ..Default::default()
54 }
55 .into(),
56 ),
57 extensions: [("contentEncoding", "base58".into())]
58 .into_iter()
59 .map(|(k, v)| (k.to_string(), v))
60 .collect(),
61 ..Default::default()
62 }
63 .into()
64 }
65
66 fn is_referenceable() -> bool {
67 false
68 }
69 }
70};