lnp/
extension.rs

1// LNP/BP Core Library implementing LNPBP specifications & standards
2// Written in 2020-2022 by
3//     Dr. Maxim Orlovsky <orlovsky@pandoracore.com>
4//
5// To the extent possible under law, the author(s) have dedicated all
6// copyright and related and neighboring rights to this software to
7// the public domain worldwide. This software is distributed without
8// any warranty.
9//
10// You should have received a copy of the MIT License
11// along with this software.
12// If not, see <https://opensource.org/licenses/MIT>.
13
14use std::convert::TryFrom;
15use std::fmt::{Debug, Display};
16use std::hash::Hash;
17
18use amplify::DumbDefault;
19use internet2::presentation::sphinx::Hop;
20use p2p::bolt::PaymentRequest;
21use wallet::psbt::Psbt;
22
23use crate::channel::tx_graph::TxGraph;
24use crate::channel::Funding;
25use crate::{channel, extension, router};
26
27/// Marker trait for creating extension nomenclatures, defining order in which
28/// extensions are called to process the data.
29///
30/// Extension nomenclature is an enum with members convertible into `u16`
31/// representation
32pub trait Nomenclature
33where
34    Self: Clone
35        + Copy
36        + PartialEq
37        + Eq
38        + PartialOrd
39        + Ord
40        + Hash
41        + Debug
42        + Display
43        + Default
44        + TryFrom<u16, Error = strict_encoding::Error>
45        + Into<u16>,
46{
47    type State: DumbDefault;
48    type Error: std::error::Error;
49    type PeerMessage;
50    type UpdateMessage;
51    type UpdateRequest;
52}
53
54pub trait Extension<N: Nomenclature> {
55    fn identity(&self) -> N;
56
57    /// Perform a sate change and produce a message which should be communicated
58    /// to peers notifying them about the state change
59    #[allow(dead_code, unused_variables)]
60    fn state_change(
61        &mut self,
62        request: &<N as extension::Nomenclature>::UpdateRequest,
63        message: &mut <N as extension::Nomenclature>::PeerMessage,
64    ) -> Result<(), <N as extension::Nomenclature>::Error> {
65        // Do nothing by default
66        Ok(())
67    }
68
69    /// Updates extension state from the data taken from the message received
70    /// from the remote peer
71    fn update_from_peer(
72        &mut self,
73        message: &<N as extension::Nomenclature>::PeerMessage,
74    ) -> Result<(), <N as extension::Nomenclature>::Error>;
75
76    /// Updates extension state from some local data
77    fn update_from_local(
78        &mut self,
79        message: &<N as extension::Nomenclature>::UpdateMessage,
80    ) -> Result<(), <N as extension::Nomenclature>::Error>;
81
82    fn load_state(&mut self, state: &N::State);
83    fn store_state(&self, state: &mut N::State);
84}
85
86pub trait RouterExtension<N>
87where
88    N: router::Nomenclature,
89    Self: Extension<N>,
90{
91    /// Constructs boxed extension objects which can be inserted into router
92    /// extension pipeline
93    #[allow(clippy::new_ret_no_self)]
94    fn new() -> Box<dyn RouterExtension<N>>
95    where
96        Self: Sized;
97
98    fn build_route(
99        &mut self,
100        payment: PaymentRequest,
101        route: &mut Vec<Hop<<N as router::Nomenclature>::HopPayload>>,
102    );
103}
104
105pub trait ChannelExtension<N>
106where
107    N: channel::Nomenclature,
108    N::State: channel::State,
109    Self: Extension<N>,
110{
111    /// Constructs boxed extension objects which can be inserted into channel
112    /// extension pipeline
113    #[allow(clippy::new_ret_no_self)]
114    fn new() -> Box<dyn ChannelExtension<N>>
115    where
116        Self: Sized;
117
118    /// Applies state to the channel transaction graph
119    fn build_graph(
120        &self,
121        tx_graph: &mut TxGraph,
122        remote: bool,
123    ) -> Result<(), <N as Nomenclature>::Error>;
124}
125
126/// Channel constructor specific methods
127pub trait ChannelConstructor<N>
128where
129    N: channel::Nomenclature,
130    N::State: channel::State,
131    Self: ChannelExtension<N> + Default,
132{
133    fn enrich_funding(
134        &self,
135        psbt: &mut Psbt,
136        funding: &Funding,
137    ) -> Result<(), <N as Nomenclature>::Error>;
138}