Merge pull request #2277 from valentinewallace/2023-05-fix-big-oms
[rust-lightning] / lightning-invoice / src / lib.rs
index 8177e835a1e86d13f1129f142f7a401c1d2dddac..f53c8953b47c66b9344d86a928d9e834790989f7 100644 (file)
@@ -394,6 +394,29 @@ pub enum Currency {
        Signet,
 }
 
+impl From<Network> for Currency {
+       fn from(network: Network) -> Self {
+               match network {
+                       Network::Bitcoin => Currency::Bitcoin,
+                       Network::Testnet => Currency::BitcoinTestnet,
+                       Network::Regtest => Currency::Regtest,
+                       Network::Signet => Currency::Signet,
+               }
+       }
+}
+
+impl From<Currency> for Network {
+       fn from(currency: Currency) -> Self {
+               match currency {
+                       Currency::Bitcoin => Network::Bitcoin,
+                       Currency::BitcoinTestnet => Network::Testnet,
+                       Currency::Regtest => Network::Regtest,
+                       Currency::Simnet => Network::Regtest,
+                       Currency::Signet => Network::Signet,
+               }
+       }
+}
+
 /// Tagged field which may have an unknown tag
 ///
 /// This is not exported to bindings users as we don't currently support TaggedField
@@ -432,6 +455,15 @@ pub enum TaggedField {
 pub struct Sha256(/// This is not exported to bindings users as the native hash types are not currently mapped
        pub sha256::Hash);
 
+impl Sha256 {
+       /// Constructs a new [`Sha256`] from the given bytes, which are assumed to be the output of a
+       /// single sha256 hash.
+       #[cfg(c_bindings)]
+       pub fn from_bytes(bytes: &[u8; 32]) -> Self {
+               Self(sha256::Hash::from_slice(bytes).expect("from_slice only fails if len is not 32"))
+       }
+}
+
 /// Description string
 ///
 /// # Invariants
@@ -495,9 +527,9 @@ pub mod constants {
 impl InvoiceBuilder<tb::False, tb::False, tb::False, tb::False, tb::False, tb::False> {
        /// Construct new, empty `InvoiceBuilder`. All necessary fields have to be filled first before
        /// `InvoiceBuilder::build(self)` becomes available.
-       pub fn new(currrency: Currency) -> Self {
+       pub fn new(currency: Currency) -> Self {
                InvoiceBuilder {
-                       currency: currrency,
+                       currency,
                        amount: None,
                        si_prefix: None,
                        timestamp: None,
@@ -1368,14 +1400,6 @@ impl Invoice {
        /// Returns a list of all fallback addresses as [`Address`]es
        pub fn fallback_addresses(&self) -> Vec<Address> {
                self.fallbacks().iter().map(|fallback| {
-                       let network = match self.currency() {
-                               Currency::Bitcoin => Network::Bitcoin,
-                               Currency::BitcoinTestnet => Network::Testnet,
-                               Currency::Regtest => Network::Regtest,
-                               Currency::Simnet => Network::Regtest,
-                               Currency::Signet => Network::Signet,
-                       };
-
                        let payload = match fallback {
                                Fallback::SegWitProgram { version, program } => {
                                        Payload::WitnessProgram { version: *version, program: program.to_vec() }
@@ -1388,7 +1412,7 @@ impl Invoice {
                                }
                        };
 
-                       Address { payload, network }
+                       Address { payload, network: self.network() }
                }).collect()
        }
 
@@ -1409,6 +1433,13 @@ impl Invoice {
                self.signed_invoice.currency()
        }
 
+       /// Returns the network for which the invoice was issued
+       ///
+       /// This is not exported to bindings users, see [`Self::currency`] instead.
+       pub fn network(&self) -> Network {
+               self.signed_invoice.currency().into()
+       }
+
        /// Returns the amount if specified in the invoice as millisatoshis.
        pub fn amount_milli_satoshis(&self) -> Option<u64> {
                self.signed_invoice.amount_pico_btc().map(|v| v / 10)
@@ -1694,7 +1725,7 @@ impl<'de> Deserialize<'de> for Invoice {
        fn deserialize<D>(deserializer: D) -> Result<Invoice, D::Error> where D: Deserializer<'de> {
                let bolt11 = String::deserialize(deserializer)?
                        .parse::<Invoice>()
-                       .map_err(|e| D::Error::custom(format!("{:?}", e)))?;
+                       .map_err(|e| D::Error::custom(format_args!("{:?}", e)))?;
 
                Ok(bolt11)
        }