Skip to content

Commit 2cb1ef7

Browse files
committed
WIP: send invoice request encoding
1 parent 3685b47 commit 2cb1ef7

File tree

3 files changed

+63
-3
lines changed

3 files changed

+63
-3
lines changed

lightning/src/offers/invoice_request.rs

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ use crate::io;
5858
use crate::ln::features::OfferFeatures;
5959
use crate::ln::msgs::DecodeError;
6060
use crate::offers::merkle::{SignatureTlvStream, SignatureTlvStreamRef, self};
61-
use crate::offers::offer::{Amount, Offer, OfferContents, OfferTlvStream, OfferTlvStreamRef};
61+
use crate::offers::offer::{Amount, Offer, OfferContents, OfferTlvStream, OfferTlvStreamRef, SendInvoiceOfferContents};
6262
use crate::offers::parse::{ParseError, ParsedMessage, SemanticError};
6363
use crate::offers::payer::{PayerContents, PayerTlvStream, PayerTlvStreamRef};
6464
use crate::util::ser::{HighZeroBytesDroppedBigSize, SeekReadable, WithoutLength, Writeable, Writer};
@@ -409,7 +409,10 @@ impl TryFrom<PartialInvoiceRequestTlvStream> for InvoiceRequestContents {
409409
) = tlv_stream;
410410

411411
let payer = PayerContents(metadata);
412-
let offer = OfferContents::try_from(offer_tlv_stream)?;
412+
let offer = match offer_tlv_stream.node_id {
413+
Some(_) => OfferContents::try_from(offer_tlv_stream)?,
414+
None => SendInvoiceOfferContents::try_from(offer_tlv_stream)?.0,
415+
};
413416

414417
if !offer.supports_chain(chain.unwrap_or_else(|| offer.implied_chain())) {
415418
return Err(SemanticError::UnsupportedChain);

lightning/src/offers/offer.rs

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -617,6 +617,57 @@ impl TryFrom<OfferTlvStream> for OfferContents {
617617
}
618618
}
619619

620+
/// [`OfferContents`] used with a "send invoice" offer (i.e., a published [`InvoiceRequest`]).
621+
///
622+
/// [`InvoiceRequest`]: crate::offers::invoice_request::InvoiceRequest
623+
pub(super) struct SendInvoiceOfferContents(pub OfferContents);
624+
625+
impl TryFrom<OfferTlvStream> for SendInvoiceOfferContents {
626+
type Error = SemanticError;
627+
628+
fn try_from(tlv_stream: OfferTlvStream) -> Result<Self, Self::Error> {
629+
let OfferTlvStream {
630+
chains, metadata, currency, amount, description, features, absolute_expiry, paths,
631+
issuer, quantity_max, node_id,
632+
} = tlv_stream;
633+
assert!(node_id.is_none());
634+
635+
if chains.is_some() {
636+
return Err(SemanticError::UnexpectedChain);
637+
}
638+
639+
if currency.is_some() || amount.is_some() {
640+
return Err(SemanticError::UnexpectedAmount);
641+
}
642+
643+
let description = match description {
644+
None => return Err(SemanticError::MissingDescription),
645+
Some(description) => description,
646+
};
647+
648+
let features = match features {
649+
None => OfferFeatures::empty(),
650+
Some(_) => return Err(SemanticError::UnexpectedFeatures),
651+
};
652+
653+
let absolute_expiry = absolute_expiry.map(Duration::from_secs);
654+
655+
let paths = match paths {
656+
Some(paths) if paths.is_empty() => return Err(SemanticError::MissingPaths),
657+
paths => paths,
658+
};
659+
660+
if quantity_max.is_some() {
661+
return Err(SemanticError::UnexpectedQuantity);
662+
}
663+
664+
Ok(SendInvoiceOfferContents(OfferContents {
665+
chains: None, metadata, amount: None, description, features, absolute_expiry, issuer,
666+
paths, supported_quantity: Quantity::one(), signing_pubkey: None,
667+
}))
668+
}
669+
}
670+
620671
impl core::fmt::Display for Offer {
621672
fn fmt(&self, f: &mut core::fmt::Formatter) -> Result<(), core::fmt::Error> {
622673
self.fmt_bech32_str(f)

lightning/src/offers/parse.rs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -102,16 +102,22 @@ pub enum ParseError {
102102
pub enum SemanticError {
103103
/// The provided chain hash does not correspond to a supported chain.
104104
UnsupportedChain,
105-
/// An amount was expected but was missing.
105+
/// A chain was provided but was not expected.
106+
UnexpectedChain,
107+
/// An amount was not provided.
106108
MissingAmount,
107109
/// An amount exceeded the maximum number of bitcoin.
108110
InvalidAmount,
109111
/// An amount was provided but was not sufficient in value.
110112
InsufficientAmount,
113+
/// An amount was provided but was not expected.
114+
UnexpectedAmount,
111115
/// A currency was provided that is not supported.
112116
UnsupportedCurrency,
113117
/// A feature was required but is unknown.
114118
UnknownRequiredFeatures,
119+
/// Features were provided but were not expected.
120+
UnexpectedFeatures,
115121
/// A required description was not provided.
116122
MissingDescription,
117123
/// A node id was not provided.

0 commit comments

Comments
 (0)