bpwallet/
layer2.rs

1// Modern, minimalistic & standard-compliant cold wallet library.
2//
3// SPDX-License-Identifier: Apache-2.0
4//
5// Written in 2020-2024 by
6//     Dr Maxim Orlovsky <orlovsky@lnp-bp.org>
7//
8// Copyright (C) 2020-2024 LNP/BP Standards Association. All rights reserved.
9// Copyright (C) 2020-2024 Dr Maxim Orlovsky. All rights reserved.
10//
11// Licensed under the Apache License, Version 2.0 (the "License");
12// you may not use this file except in compliance with the License.
13// You may obtain a copy of the License at
14//
15//     http://www.apache.org/licenses/LICENSE-2.0
16//
17// Unless required by applicable law or agreed to in writing, software
18// distributed under the License is distributed on an "AS IS" BASIS,
19// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
20// See the License for the specific language governing permissions and
21// limitations under the License.
22
23use std::convert::Infallible;
24use std::error;
25use std::fmt::Debug;
26
27use nonasync::persistence::{CloneNoPersistence, Persistence, Persisting};
28
29pub trait Layer2: Debug + CloneNoPersistence + Persisting {
30    type Descr: Layer2Descriptor;
31    type Data: Layer2Data;
32    type Cache: Layer2Cache;
33    type LoadError: error::Error;
34    type StoreError: error::Error;
35}
36
37pub trait Layer2Descriptor: Debug + Clone {}
38
39pub trait Layer2Data: Debug + Clone + Default {}
40
41pub trait Layer2Cache: Debug + Clone + Default {
42    type Tx: Layer2Tx;
43    type Coin: Layer2Coin;
44}
45
46#[cfg(not(feature = "serde"))]
47pub trait Layer2Tx: Debug + Default {}
48
49#[cfg(feature = "serde")]
50pub trait Layer2Tx: Debug + Default + serde::Serialize + for<'de> serde::Deserialize<'de> {}
51
52#[cfg(not(feature = "serde"))]
53pub trait Layer2Coin: Debug + Default {}
54
55#[cfg(feature = "serde")]
56pub trait Layer2Coin:
57    Debug + Default + serde::Serialize + for<'de> serde::Deserialize<'de>
58{
59}
60
61#[derive(Copy, Clone, PartialEq, Eq, Hash, Debug, Default)]
62pub struct Layer2Empty;
63
64#[cfg(feature = "serde")]
65mod _empty_serde {
66    use std::collections::HashMap;
67    use std::fmt::{self, Formatter};
68
69    use serde_crate::de::{Error, Expected, Unexpected};
70    use serde_crate::{Deserialize, Deserializer, Serialize, Serializer};
71
72    use super::*;
73
74    impl Expected for Layer2Empty {
75        fn fmt(&self, f: &mut Formatter) -> fmt::Result { f.write_str("unit struct") }
76    }
77
78    impl Serialize for Layer2Empty {
79        fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
80        where S: Serializer {
81            HashMap::<String, toml::Value>::new().serialize(serializer)
82        }
83    }
84
85    impl<'de> Deserialize<'de> for Layer2Empty {
86        fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
87        where D: Deserializer<'de> {
88            let map: HashMap<String, toml::Value> = Deserialize::deserialize(deserializer)?;
89            if !map.is_empty() {
90                return Err(D::Error::invalid_type(Unexpected::Map, &Layer2Empty));
91            }
92            Ok(Layer2Empty)
93        }
94    }
95}
96
97#[derive(Debug, Default)]
98#[cfg_attr(
99    feature = "serde",
100    derive(serde::Serialize, serde::Deserialize),
101    serde(crate = "serde_crate")
102)]
103pub struct NoLayer2 {
104    #[cfg_attr(feature = "serde", serde(skip))]
105    persistence: Option<Persistence<Self>>,
106}
107
108impl CloneNoPersistence for NoLayer2 {
109    fn clone_no_persistence(&self) -> Self { none!() }
110}
111
112impl Persisting for NoLayer2 {
113    #[inline]
114    fn persistence(&self) -> Option<&Persistence<Self>> { self.persistence.as_ref() }
115    #[inline]
116    fn persistence_mut(&mut self) -> Option<&mut Persistence<Self>> { self.persistence.as_mut() }
117    #[inline]
118    fn as_mut_persistence(&mut self) -> &mut Option<Persistence<Self>> { &mut self.persistence }
119}
120
121impl Layer2 for NoLayer2 {
122    type Descr = Layer2Empty;
123    type Data = Layer2Empty;
124    type Cache = Layer2Empty;
125    type LoadError = Infallible;
126    type StoreError = Infallible;
127}
128
129impl Layer2Descriptor for Layer2Empty {}
130
131impl Layer2Data for Layer2Empty {}
132
133impl Layer2Cache for Layer2Empty {
134    type Tx = Layer2Empty;
135    type Coin = Layer2Empty;
136}
137
138impl Layer2Tx for Layer2Empty {}
139impl Layer2Coin for Layer2Empty {}