1use crate::blinded_path::message::BlindedMessagePath;
69use crate::blinded_path::payment::BlindedPaymentPath;
70use crate::io;
71use crate::ln::channelmanager::PaymentId;
72use crate::ln::inbound_payment::{ExpandedKey, IV_LEN};
73use crate::ln::msgs::DecodeError;
74use crate::offers::merkle::{
75 self, SignError, SignFn, SignatureTlvStream, SignatureTlvStreamRef, TaggedHash, TlvStream,
76};
77use crate::offers::nonce::Nonce;
78use crate::offers::offer::{
79 Amount, ExperimentalOfferTlvStream, ExperimentalOfferTlvStreamRef, Offer, OfferContents,
80 OfferId, OfferTlvStream, OfferTlvStreamRef, EXPERIMENTAL_OFFER_TYPES, OFFER_TYPES,
81};
82use crate::offers::parse::{Bolt12ParseError, Bolt12SemanticError, ParsedMessage};
83use crate::offers::payer::{PayerContents, PayerTlvStream, PayerTlvStreamRef};
84use crate::offers::signer::{Metadata, MetadataMaterial};
85use crate::onion_message::dns_resolution::HumanReadableName;
86use crate::types::features::InvoiceRequestFeatures;
87use crate::types::payment::PaymentHash;
88use crate::types::string::{PrintableString, UntrustedString};
89use crate::util::ser::{
90 CursorReadable, HighZeroBytesDroppedBigSize, LengthLimitedRead, LengthReadable, Readable,
91 WithoutLength, Writeable, Writer,
92};
93use bitcoin::constants::ChainHash;
94use bitcoin::network::Network;
95use bitcoin::secp256k1::schnorr::Signature;
96use bitcoin::secp256k1::{self, Keypair, PublicKey, Secp256k1};
97
98#[cfg(not(c_bindings))]
99use crate::offers::invoice::{DerivedSigningPubkey, ExplicitSigningPubkey, InvoiceBuilder};
100#[cfg(c_bindings)]
101use crate::offers::invoice::{
102 InvoiceWithDerivedSigningPubkeyBuilder, InvoiceWithExplicitSigningPubkeyBuilder,
103};
104
105#[allow(unused_imports)]
106use crate::prelude::*;
107
108pub const SIGNATURE_TAG: &'static str = concat!("lightning", "invoice_request", "signature");
110
111pub(super) const IV_BYTES: &[u8; IV_LEN] = b"LDK Invreq ~~~~~";
112
113pub struct InvoiceRequestBuilder<'a, 'b, T: secp256k1::Signing> {
121 offer: &'a Offer,
122 invoice_request: InvoiceRequestContentsWithoutPayerSigningPubkey,
123 payer_signing_pubkey: Option<PublicKey>,
124 secp_ctx: Option<&'b Secp256k1<T>>,
125}
126
127#[cfg(c_bindings)]
133pub struct InvoiceRequestWithDerivedPayerSigningPubkeyBuilder<'a, 'b> {
134 offer: &'a Offer,
135 invoice_request: InvoiceRequestContentsWithoutPayerSigningPubkey,
136 payer_signing_pubkey: Option<PublicKey>,
137 secp_ctx: Option<&'b Secp256k1<secp256k1::All>>,
138}
139
140macro_rules! invoice_request_derived_payer_signing_pubkey_builder_methods {
141 (
142 $self: ident, $self_type: ty, $secp_context: ty
143) => {
144 #[cfg_attr(c_bindings, allow(dead_code))]
145 pub(super) fn deriving_signing_pubkey(
146 offer: &'a Offer, expanded_key: &ExpandedKey, nonce: Nonce,
147 secp_ctx: &'b Secp256k1<$secp_context>, payment_id: PaymentId,
148 ) -> Self {
149 let payment_id = Some(payment_id);
150 let derivation_material = MetadataMaterial::new(nonce, expanded_key, payment_id);
151 let metadata = Metadata::DerivedSigningPubkey(derivation_material);
152 Self {
153 offer,
154 invoice_request: Self::create_contents(offer, metadata),
155 payer_signing_pubkey: None,
156 secp_ctx: Some(secp_ctx),
157 }
158 }
159
160 pub fn build_and_sign($self: $self_type) -> Result<InvoiceRequest, Bolt12SemanticError> {
162 let (unsigned_invoice_request, keys, secp_ctx) = $self.build_with_checks()?;
163 #[cfg(c_bindings)]
164 let mut unsigned_invoice_request = unsigned_invoice_request;
165 debug_assert!(keys.is_some());
166
167 let secp_ctx = secp_ctx.unwrap();
168 let keys = keys.unwrap();
169 let invoice_request = unsigned_invoice_request
170 .sign(|message: &UnsignedInvoiceRequest| {
171 Ok(secp_ctx.sign_schnorr_no_aux_rand(message.as_ref().as_digest(), &keys))
172 })
173 .unwrap();
174 Ok(invoice_request)
175 }
176 };
177}
178
179macro_rules! invoice_request_builder_methods { (
180 $self: ident, $self_type: ty, $return_type: ty, $return_value: expr, $secp_context: ty $(, $self_mut: tt)?
181) => {
182 #[cfg_attr(c_bindings, allow(dead_code))]
183 fn create_contents(offer: &Offer, metadata: Metadata) -> InvoiceRequestContentsWithoutPayerSigningPubkey {
184 let offer = offer.contents.clone();
185 InvoiceRequestContentsWithoutPayerSigningPubkey {
186 payer: PayerContents(metadata), offer, chain: None, amount_msats: None,
187 features: InvoiceRequestFeatures::empty(), quantity: None, payer_note: None,
188 offer_from_hrn: None,
189 #[cfg(test)]
190 experimental_bar: None,
191 }
192 }
193
194 pub fn chain($self: $self_type, network: Network) -> Result<$return_type, Bolt12SemanticError> {
200 $self.chain_hash(ChainHash::using_genesis_block(network))
201 }
202
203 pub(crate) fn chain_hash($($self_mut)* $self: $self_type, chain: ChainHash) -> Result<$return_type, Bolt12SemanticError> {
209 if !$self.offer.supports_chain(chain) {
210 return Err(Bolt12SemanticError::UnsupportedChain);
211 }
212
213 $self.invoice_request.chain = Some(chain);
214 Ok($return_value)
215 }
216
217 pub fn amount_msats($($self_mut)* $self: $self_type, amount_msats: u64) -> Result<$return_type, Bolt12SemanticError> {
224 $self.invoice_request.offer.check_amount_msats_for_quantity(
225 Some(amount_msats), $self.invoice_request.quantity
226 )?;
227 $self.invoice_request.amount_msats = Some(amount_msats);
228 Ok($return_value)
229 }
230
231 pub fn quantity($($self_mut)* $self: $self_type, quantity: u64) -> Result<$return_type, Bolt12SemanticError> {
236 $self.invoice_request.offer.check_quantity(Some(quantity))?;
237 $self.invoice_request.quantity = Some(quantity);
238 Ok($return_value)
239 }
240
241 pub fn payer_note($($self_mut)* $self: $self_type, payer_note: String) -> $return_type {
245 $self.invoice_request.payer_note = Some(payer_note);
246 $return_value
247 }
248
249 pub fn sourced_from_human_readable_name($($self_mut)* $self: $self_type, hrn: HumanReadableName) -> $return_type {
253 $self.invoice_request.offer_from_hrn = Some(hrn);
254 $return_value
255 }
256
257 fn build_with_checks($($self_mut)* $self: $self_type) -> Result<
258 (UnsignedInvoiceRequest, Option<Keypair>, Option<&'b Secp256k1<$secp_context>>),
259 Bolt12SemanticError
260 > {
261 #[cfg(feature = "std")] {
262 if $self.offer.is_expired() {
263 return Err(Bolt12SemanticError::AlreadyExpired);
264 }
265 }
266
267 let chain = $self.invoice_request.chain();
268 if !$self.offer.supports_chain(chain) {
269 return Err(Bolt12SemanticError::UnsupportedChain);
270 }
271
272 if chain == $self.offer.implied_chain() {
273 $self.invoice_request.chain = None;
274 }
275
276 if $self.offer.amount().is_none() && $self.invoice_request.amount_msats.is_none() {
277 return Err(Bolt12SemanticError::MissingAmount);
278 }
279
280 $self.invoice_request.offer.check_quantity($self.invoice_request.quantity)?;
281 $self.invoice_request.offer.check_amount_msats_for_quantity(
282 $self.invoice_request.amount_msats, $self.invoice_request.quantity
283 )?;
284
285 Ok($self.build_without_checks())
286 }
287
288 fn build_without_checks($($self_mut)* $self: $self_type) ->
289 (UnsignedInvoiceRequest, Option<Keypair>, Option<&'b Secp256k1<$secp_context>>)
290 {
291 let mut keys = None;
293 let secp_ctx = $self.secp_ctx.clone();
294 if $self.invoice_request.payer.0.has_derivation_material() {
295 let mut metadata = core::mem::take(&mut $self.invoice_request.payer.0);
296
297 let mut tlv_stream = $self.invoice_request.as_tlv_stream();
298 debug_assert!(tlv_stream.2.payer_id.is_none());
299 tlv_stream.0.metadata = None;
300 if !metadata.derives_payer_keys() {
301 tlv_stream.2.payer_id = $self.payer_signing_pubkey.as_ref();
302 }
303
304 let (derived_metadata, derived_keys) =
305 metadata.derive_from(IV_BYTES, tlv_stream, $self.secp_ctx);
306 metadata = derived_metadata;
307 keys = derived_keys;
308 if let Some(keys) = keys {
309 debug_assert!($self.payer_signing_pubkey.is_none());
310 $self.payer_signing_pubkey = Some(keys.public_key());
311 }
312
313 $self.invoice_request.payer.0 = metadata;
314 }
315
316 debug_assert!($self.invoice_request.payer.0.as_bytes().is_some());
317 debug_assert!($self.payer_signing_pubkey.is_some());
318 let payer_signing_pubkey = $self.payer_signing_pubkey.unwrap();
319
320 let invoice_request = InvoiceRequestContents {
321 #[cfg(not(c_bindings))]
322 inner: $self.invoice_request,
323 #[cfg(c_bindings)]
324 inner: $self.invoice_request.clone(),
325 payer_signing_pubkey,
326 };
327 let unsigned_invoice_request = UnsignedInvoiceRequest::new($self.offer, invoice_request);
328
329 (unsigned_invoice_request, keys, secp_ctx)
330 }
331} }
332
333#[cfg(test)]
334macro_rules! invoice_request_builder_test_methods { (
335 $self: ident, $self_type: ty, $return_type: ty, $return_value: expr $(, $self_mut: tt)?
336) => {
337 #[cfg_attr(c_bindings, allow(dead_code))]
338 pub(super) fn payer_metadata($($self_mut)* $self: $self_type, metadata: Metadata) -> $return_type {
339 $self.invoice_request.payer = PayerContents(metadata);
340 $return_value
341 }
342
343 #[cfg_attr(c_bindings, allow(dead_code))]
344 fn chain_unchecked($($self_mut)* $self: $self_type, network: Network) -> $return_type {
345 let chain = ChainHash::using_genesis_block(network);
346 $self.invoice_request.chain = Some(chain);
347 $return_value
348 }
349
350 #[cfg_attr(c_bindings, allow(dead_code))]
351 fn amount_msats_unchecked($($self_mut)* $self: $self_type, amount_msats: u64) -> $return_type {
352 $self.invoice_request.amount_msats = Some(amount_msats);
353 $return_value
354 }
355
356 #[cfg_attr(c_bindings, allow(dead_code))]
357 fn features_unchecked($($self_mut)* $self: $self_type, features: InvoiceRequestFeatures) -> $return_type {
358 $self.invoice_request.features = features;
359 $return_value
360 }
361
362 #[cfg_attr(c_bindings, allow(dead_code))]
363 fn quantity_unchecked($($self_mut)* $self: $self_type, quantity: u64) -> $return_type {
364 $self.invoice_request.quantity = Some(quantity);
365 $return_value
366 }
367
368 #[cfg_attr(c_bindings, allow(dead_code))]
369 pub(super) fn payer_signing_pubkey($($self_mut)* $self: $self_type, signing_pubkey: PublicKey) -> $return_type {
370 $self.payer_signing_pubkey = Some(signing_pubkey);
371 $return_value
372 }
373
374 #[cfg_attr(c_bindings, allow(dead_code))]
375 pub(super) fn experimental_bar($($self_mut)* $self: $self_type, experimental_bar: u64) -> $return_type {
376 $self.invoice_request.experimental_bar = Some(experimental_bar);
377 $return_value
378 }
379
380 #[cfg_attr(c_bindings, allow(dead_code))]
381 pub(super) fn build_unchecked($self: $self_type) -> UnsignedInvoiceRequest {
382 $self.build_without_checks().0
383 }
384
385 #[cfg_attr(c_bindings, allow(dead_code))]
386 pub(super) fn build_unchecked_and_sign($self: $self_type) -> InvoiceRequest {
387 let (unsigned_invoice_request, keys, secp_ctx) = $self.build_without_checks();
388 #[cfg(c_bindings)]
389 let mut unsigned_invoice_request = unsigned_invoice_request;
390 debug_assert!(keys.is_some());
391
392 let secp_ctx = secp_ctx.unwrap();
393 let keys = keys.unwrap();
394 unsigned_invoice_request
395 .sign(|message: &UnsignedInvoiceRequest|
396 Ok(secp_ctx.sign_schnorr_no_aux_rand(message.as_ref().as_digest(), &keys))
397 )
398 .unwrap()
399 }
400} }
401
402impl<'a, 'b, T: secp256k1::Signing> InvoiceRequestBuilder<'a, 'b, T> {
403 invoice_request_derived_payer_signing_pubkey_builder_methods!(self, Self, T);
404 invoice_request_builder_methods!(self, Self, Self, self, T, mut);
405
406 #[cfg(test)]
407 invoice_request_builder_test_methods!(self, Self, Self, self, mut);
408}
409
410#[cfg(all(c_bindings, not(test)))]
411impl<'a, 'b> InvoiceRequestWithDerivedPayerSigningPubkeyBuilder<'a, 'b> {
412 invoice_request_derived_payer_signing_pubkey_builder_methods!(self, &mut Self, secp256k1::All);
413 invoice_request_builder_methods!(self, &mut Self, (), (), secp256k1::All);
414}
415
416#[cfg(all(c_bindings, test))]
417impl<'a, 'b> InvoiceRequestWithDerivedPayerSigningPubkeyBuilder<'a, 'b> {
418 invoice_request_derived_payer_signing_pubkey_builder_methods!(self, &mut Self, secp256k1::All);
419 invoice_request_builder_methods!(self, &mut Self, &mut Self, self, secp256k1::All);
420 invoice_request_builder_test_methods!(self, &mut Self, &mut Self, self);
421}
422
423#[cfg(c_bindings)]
424impl<'a, 'b> From<InvoiceRequestWithDerivedPayerSigningPubkeyBuilder<'a, 'b>>
425 for InvoiceRequestBuilder<'a, 'b, secp256k1::All>
426{
427 fn from(builder: InvoiceRequestWithDerivedPayerSigningPubkeyBuilder<'a, 'b>) -> Self {
428 let InvoiceRequestWithDerivedPayerSigningPubkeyBuilder {
429 offer,
430 invoice_request,
431 payer_signing_pubkey,
432 secp_ctx,
433 } = builder;
434
435 Self { offer, invoice_request, payer_signing_pubkey, secp_ctx }
436 }
437}
438
439#[derive(Clone)]
446pub struct UnsignedInvoiceRequest {
447 bytes: Vec<u8>,
448 experimental_bytes: Vec<u8>,
449 contents: InvoiceRequestContents,
450 tagged_hash: TaggedHash,
451}
452
453pub trait SignInvoiceRequestFn {
455 fn sign_invoice_request(&self, message: &UnsignedInvoiceRequest) -> Result<Signature, ()>;
457}
458
459impl<F> SignInvoiceRequestFn for F
460where
461 F: Fn(&UnsignedInvoiceRequest) -> Result<Signature, ()>,
462{
463 fn sign_invoice_request(&self, message: &UnsignedInvoiceRequest) -> Result<Signature, ()> {
464 self(message)
465 }
466}
467
468impl<F> SignFn<UnsignedInvoiceRequest> for F
469where
470 F: SignInvoiceRequestFn,
471{
472 fn sign(&self, message: &UnsignedInvoiceRequest) -> Result<Signature, ()> {
473 self.sign_invoice_request(message)
474 }
475}
476
477impl UnsignedInvoiceRequest {
478 fn new(offer: &Offer, contents: InvoiceRequestContents) -> Self {
479 let (
482 payer_tlv_stream,
483 _offer_tlv_stream,
484 invoice_request_tlv_stream,
485 _experimental_offer_tlv_stream,
486 experimental_invoice_request_tlv_stream,
487 ) = contents.as_tlv_stream();
488
489 const INVOICE_REQUEST_ALLOCATION_SIZE: usize = 512;
490 let mut bytes = Vec::with_capacity(INVOICE_REQUEST_ALLOCATION_SIZE);
491
492 payer_tlv_stream.write(&mut bytes).unwrap();
493
494 for record in TlvStream::new(&offer.bytes).range(OFFER_TYPES) {
495 record.write(&mut bytes).unwrap();
496 }
497
498 let remaining_bytes = &offer.bytes[bytes.len() - payer_tlv_stream.serialized_length()..];
499
500 invoice_request_tlv_stream.write(&mut bytes).unwrap();
501
502 const EXPERIMENTAL_TLV_ALLOCATION_SIZE: usize = 0;
503 let mut experimental_bytes = Vec::with_capacity(EXPERIMENTAL_TLV_ALLOCATION_SIZE);
504
505 let experimental_tlv_stream =
506 TlvStream::new(remaining_bytes).range(EXPERIMENTAL_OFFER_TYPES);
507 for record in experimental_tlv_stream {
508 record.write(&mut experimental_bytes).unwrap();
509 }
510
511 experimental_invoice_request_tlv_stream.write(&mut experimental_bytes).unwrap();
512
513 let tlv_stream = TlvStream::new(&bytes).chain(TlvStream::new(&experimental_bytes));
514 let tagged_hash = TaggedHash::from_tlv_stream(SIGNATURE_TAG, tlv_stream);
515
516 Self { bytes, experimental_bytes, contents, tagged_hash }
517 }
518
519 pub fn tagged_hash(&self) -> &TaggedHash {
521 &self.tagged_hash
522 }
523}
524
525macro_rules! unsigned_invoice_request_sign_method { (
526 $self: ident, $self_type: ty $(, $self_mut: tt)?
527) => {
528 pub fn sign<F: SignInvoiceRequestFn>(
532 $($self_mut)* $self: $self_type, sign: F
533 ) -> Result<InvoiceRequest, SignError> {
534 let pubkey = $self.contents.payer_signing_pubkey;
535 let signature = merkle::sign_message(sign, &$self, pubkey)?;
536
537 let signature_tlv_stream = SignatureTlvStreamRef {
539 signature: Some(&signature),
540 };
541 signature_tlv_stream.write(&mut $self.bytes).unwrap();
542
543 $self.bytes.extend_from_slice(&$self.experimental_bytes);
545
546 Ok(InvoiceRequest {
547 #[cfg(not(c_bindings))]
548 bytes: $self.bytes,
549 #[cfg(c_bindings)]
550 bytes: $self.bytes.clone(),
551 #[cfg(not(c_bindings))]
552 contents: $self.contents,
553 #[cfg(c_bindings)]
554 contents: $self.contents.clone(),
555 signature,
556 })
557 }
558} }
559
560#[cfg(not(c_bindings))]
561impl UnsignedInvoiceRequest {
562 unsigned_invoice_request_sign_method!(self, Self, mut);
563}
564
565#[cfg(c_bindings)]
566impl UnsignedInvoiceRequest {
567 unsigned_invoice_request_sign_method!(self, &mut Self);
568}
569
570impl AsRef<TaggedHash> for UnsignedInvoiceRequest {
571 fn as_ref(&self) -> &TaggedHash {
572 &self.tagged_hash
573 }
574}
575
576#[derive(Clone, Debug)]
584#[cfg_attr(test, derive(PartialEq))]
585pub struct InvoiceRequest {
586 pub(super) bytes: Vec<u8>,
587 pub(super) contents: InvoiceRequestContents,
588 signature: Signature,
589}
590
591#[cfg(not(test))]
592impl PartialEq for InvoiceRequest {
593 fn eq(&self, other: &Self) -> bool {
594 self.bytes.eq(&other.bytes) && self.signature.eq(&other.signature)
595 }
596}
597
598impl Eq for InvoiceRequest {}
599
600#[derive(Clone, Debug)]
604pub struct VerifiedInvoiceRequest {
605 pub offer_id: OfferId,
607
608 pub(crate) inner: InvoiceRequest,
610
611 #[cfg_attr(
614 feature = "std",
615 doc = "If `Some`, must call [`respond_using_derived_keys`] when responding. Otherwise, call [`respond_with`]."
616 )]
617 #[cfg_attr(feature = "std", doc = "")]
618 #[cfg_attr(
620 feature = "std",
621 doc = "[`respond_using_derived_keys`]: Self::respond_using_derived_keys"
622 )]
623 #[cfg_attr(feature = "std", doc = "[`respond_with`]: Self::respond_with")]
624 pub keys: Option<Keypair>,
625}
626
627#[derive(Clone, Debug)]
631#[cfg_attr(test, derive(PartialEq))]
632pub(super) struct InvoiceRequestContents {
633 pub(super) inner: InvoiceRequestContentsWithoutPayerSigningPubkey,
634 payer_signing_pubkey: PublicKey,
635}
636
637#[derive(Clone, Debug)]
638#[cfg_attr(test, derive(PartialEq))]
639pub(super) struct InvoiceRequestContentsWithoutPayerSigningPubkey {
640 pub(super) payer: PayerContents,
641 pub(super) offer: OfferContents,
642 chain: Option<ChainHash>,
643 amount_msats: Option<u64>,
644 features: InvoiceRequestFeatures,
645 quantity: Option<u64>,
646 payer_note: Option<String>,
647 offer_from_hrn: Option<HumanReadableName>,
648 #[cfg(test)]
649 experimental_bar: Option<u64>,
650}
651
652macro_rules! invoice_request_accessors { ($self: ident, $contents: expr) => {
653 pub fn payer_metadata(&$self) -> &[u8] {
658 $contents.metadata()
659 }
660
661 pub fn chain(&$self) -> ChainHash {
663 $contents.chain()
664 }
665
666 pub fn amount_msats(&$self) -> Option<u64> {
671 $contents.amount_msats()
672 }
673
674 pub fn has_amount_msats(&$self) -> bool {
680 $contents.has_amount_msats()
681 }
682
683 pub fn invoice_request_features(&$self) -> &InvoiceRequestFeatures {
685 &$contents.features()
686 }
687
688 pub fn quantity(&$self) -> Option<u64> {
690 $contents.quantity()
691 }
692
693 pub fn payer_signing_pubkey(&$self) -> PublicKey {
695 $contents.payer_signing_pubkey()
696 }
697
698 pub fn payer_note(&$self) -> Option<PrintableString<'_>> {
701 $contents.payer_note()
702 }
703
704 pub fn offer_from_hrn(&$self) -> &Option<HumanReadableName> {
707 $contents.offer_from_hrn()
708 }
709} }
710
711impl UnsignedInvoiceRequest {
712 offer_accessors!(self, self.contents.inner.offer);
713 invoice_request_accessors!(self, self.contents);
714}
715
716macro_rules! invoice_request_respond_with_explicit_signing_pubkey_methods { (
717 $self: ident, $contents: expr, $builder: ty
718) => {
719 #[cfg(feature = "std")]
727 pub fn respond_with(
728 &$self, payment_paths: Vec<BlindedPaymentPath>, payment_hash: PaymentHash
729 ) -> Result<$builder, Bolt12SemanticError> {
730 let created_at = std::time::SystemTime::now()
731 .duration_since(std::time::SystemTime::UNIX_EPOCH)
732 .expect("SystemTime::now() should come after SystemTime::UNIX_EPOCH");
733
734 $contents.respond_with_no_std(payment_paths, payment_hash, created_at)
735 }
736
737 #[cfg_attr(feature = "std", doc = "Useful for non-`std` builds where [`std::time::SystemTime`] is not available.")]
742 pub fn respond_with_no_std(
763 &$self, payment_paths: Vec<BlindedPaymentPath>, payment_hash: PaymentHash,
764 created_at: core::time::Duration
765 ) -> Result<$builder, Bolt12SemanticError> {
766 if $contents.invoice_request_features().requires_unknown_bits() {
767 return Err(Bolt12SemanticError::UnknownRequiredFeatures);
768 }
769
770 let signing_pubkey = match $contents.contents.inner.offer.issuer_signing_pubkey() {
771 Some(signing_pubkey) => signing_pubkey,
772 None => return Err(Bolt12SemanticError::MissingIssuerSigningPubkey),
773 };
774
775 <$builder>::for_offer(&$contents, payment_paths, created_at, payment_hash, signing_pubkey)
776 }
777
778 #[cfg(test)]
779 #[allow(dead_code)]
780 pub(super) fn respond_with_no_std_using_signing_pubkey(
781 &$self, payment_paths: Vec<BlindedPaymentPath>, payment_hash: PaymentHash,
782 created_at: core::time::Duration, signing_pubkey: PublicKey
783 ) -> Result<$builder, Bolt12SemanticError> {
784 debug_assert!($contents.contents.inner.offer.issuer_signing_pubkey().is_none());
785
786 if $contents.invoice_request_features().requires_unknown_bits() {
787 return Err(Bolt12SemanticError::UnknownRequiredFeatures);
788 }
789
790 <$builder>::for_offer(&$contents, payment_paths, created_at, payment_hash, signing_pubkey)
791 }
792} }
793
794macro_rules! invoice_request_verify_method {
795 ($self: ident, $self_type: ty) => {
796#[rustfmt::skip]
804 pub fn verify_using_metadata<
805 #[cfg(not(c_bindings))]
806 T: secp256k1::Signing
807 >(
808 $self: $self_type, key: &ExpandedKey,
809 #[cfg(not(c_bindings))]
810 secp_ctx: &Secp256k1<T>,
811 #[cfg(c_bindings)]
812 secp_ctx: &Secp256k1<secp256k1::All>,
813 ) -> Result<VerifiedInvoiceRequest, ()> {
814 let (offer_id, keys) =
815 $self.contents.inner.offer.verify_using_metadata(&$self.bytes, key, secp_ctx)?;
816 Ok(VerifiedInvoiceRequest {
817 offer_id,
818 #[cfg(not(c_bindings))]
819 inner: $self,
820 #[cfg(c_bindings)]
821 inner: $self.clone(),
822 keys,
823 })
824 }
825
826#[rustfmt::skip]
834 pub fn verify_using_recipient_data<
835 #[cfg(not(c_bindings))]
836 T: secp256k1::Signing
837 >(
838 $self: $self_type, nonce: Nonce, key: &ExpandedKey,
839 #[cfg(not(c_bindings))]
840 secp_ctx: &Secp256k1<T>,
841 #[cfg(c_bindings)]
842 secp_ctx: &Secp256k1<secp256k1::All>,
843 ) -> Result<VerifiedInvoiceRequest, ()> {
844 let (offer_id, keys) = $self.contents.inner.offer.verify_using_recipient_data(
845 &$self.bytes, nonce, key, secp_ctx
846 )?;
847 Ok(VerifiedInvoiceRequest {
848 offer_id,
849 #[cfg(not(c_bindings))]
850 inner: $self,
851 #[cfg(c_bindings)]
852 inner: $self.clone(),
853 keys,
854 })
855 }
856 };
857}
858
859#[cfg(not(c_bindings))]
860impl InvoiceRequest {
861 offer_accessors!(self, self.contents.inner.offer);
862 invoice_request_accessors!(self, self.contents);
863 invoice_request_respond_with_explicit_signing_pubkey_methods!(
864 self,
865 self,
866 InvoiceBuilder<'_, ExplicitSigningPubkey>
867 );
868 invoice_request_verify_method!(self, Self);
869
870 #[allow(unused)] pub(super) fn bytes(&self) -> &Vec<u8> {
872 &self.bytes
873 }
874}
875
876#[cfg(c_bindings)]
877impl InvoiceRequest {
878 offer_accessors!(self, self.contents.inner.offer);
879 invoice_request_accessors!(self, self.contents);
880 invoice_request_respond_with_explicit_signing_pubkey_methods!(
881 self,
882 self,
883 InvoiceWithExplicitSigningPubkeyBuilder
884 );
885 invoice_request_verify_method!(self, &Self);
886
887 #[allow(unused)] pub(super) fn bytes(&self) -> &Vec<u8> {
889 &self.bytes
890 }
891}
892
893impl InvoiceRequest {
894 pub fn signature(&self) -> Signature {
898 self.signature
899 }
900
901 pub(crate) fn as_tlv_stream(&self) -> FullInvoiceRequestTlvStreamRef<'_> {
902 let (
903 payer_tlv_stream,
904 offer_tlv_stream,
905 invoice_request_tlv_stream,
906 experimental_offer_tlv_stream,
907 experimental_invoice_request_tlv_stream,
908 ) = self.contents.as_tlv_stream();
909 let signature_tlv_stream = SignatureTlvStreamRef { signature: Some(&self.signature) };
910 (
911 payer_tlv_stream,
912 offer_tlv_stream,
913 invoice_request_tlv_stream,
914 signature_tlv_stream,
915 experimental_offer_tlv_stream,
916 experimental_invoice_request_tlv_stream,
917 )
918 }
919}
920
921macro_rules! invoice_request_respond_with_derived_signing_pubkey_methods { (
922 $self: ident, $contents: expr, $builder: ty
923) => {
924 #[cfg(feature = "std")]
932 pub fn respond_using_derived_keys(
933 &$self, payment_paths: Vec<BlindedPaymentPath>, payment_hash: PaymentHash
934 ) -> Result<$builder, Bolt12SemanticError> {
935 let created_at = std::time::SystemTime::now()
936 .duration_since(std::time::SystemTime::UNIX_EPOCH)
937 .expect("SystemTime::now() should come after SystemTime::UNIX_EPOCH");
938
939 $self.respond_using_derived_keys_no_std(payment_paths, payment_hash, created_at)
940 }
941
942 pub fn respond_using_derived_keys_no_std(
950 &$self, payment_paths: Vec<BlindedPaymentPath>, payment_hash: PaymentHash,
951 created_at: core::time::Duration
952 ) -> Result<$builder, Bolt12SemanticError> {
953 if $self.inner.invoice_request_features().requires_unknown_bits() {
954 return Err(Bolt12SemanticError::UnknownRequiredFeatures);
955 }
956
957 let keys = match $self.keys {
958 None => return Err(Bolt12SemanticError::InvalidMetadata),
959 Some(keys) => keys,
960 };
961
962 match $contents.contents.inner.offer.issuer_signing_pubkey() {
963 Some(signing_pubkey) => debug_assert_eq!(signing_pubkey, keys.public_key()),
964 None => return Err(Bolt12SemanticError::MissingIssuerSigningPubkey),
965 }
966
967 <$builder>::for_offer_using_keys(
968 &$self.inner, payment_paths, created_at, payment_hash, keys
969 )
970 }
971} }
972
973impl VerifiedInvoiceRequest {
974 offer_accessors!(self, self.inner.contents.inner.offer);
975 invoice_request_accessors!(self, self.inner.contents);
976 #[cfg(not(c_bindings))]
977 invoice_request_respond_with_explicit_signing_pubkey_methods!(
978 self,
979 self.inner,
980 InvoiceBuilder<'_, ExplicitSigningPubkey>
981 );
982 #[cfg(c_bindings)]
983 invoice_request_respond_with_explicit_signing_pubkey_methods!(
984 self,
985 self.inner,
986 InvoiceWithExplicitSigningPubkeyBuilder
987 );
988 #[cfg(not(c_bindings))]
989 invoice_request_respond_with_derived_signing_pubkey_methods!(
990 self,
991 self.inner,
992 InvoiceBuilder<'_, DerivedSigningPubkey>
993 );
994 #[cfg(c_bindings)]
995 invoice_request_respond_with_derived_signing_pubkey_methods!(
996 self,
997 self.inner,
998 InvoiceWithDerivedSigningPubkeyBuilder
999 );
1000
1001 pub fn fields(&self) -> InvoiceRequestFields {
1009 let InvoiceRequestContents {
1010 payer_signing_pubkey,
1011 inner: InvoiceRequestContentsWithoutPayerSigningPubkey { quantity, payer_note, .. },
1012 } = &self.inner.contents;
1013
1014 InvoiceRequestFields {
1015 payer_signing_pubkey: *payer_signing_pubkey,
1016 quantity: *quantity,
1017 payer_note_truncated: payer_note
1018 .clone()
1019 .map(|s| UntrustedString(string_truncate_safe(s, PAYER_NOTE_LIMIT))),
1022 human_readable_name: self.offer_from_hrn().clone(),
1023 }
1024 }
1025}
1026
1027fn string_truncate_safe(mut s: String, new_len: usize) -> String {
1036 let truncated_len = if new_len >= s.len() {
1040 s.len()
1041 } else {
1042 (0..=new_len).rev().find(|idx| s.is_char_boundary(*idx)).unwrap_or(0)
1043 };
1044 s.truncate(truncated_len);
1045 s
1046}
1047
1048impl InvoiceRequestContents {
1049 pub(super) fn metadata(&self) -> &[u8] {
1050 self.inner.metadata()
1051 }
1052
1053 pub(super) fn chain(&self) -> ChainHash {
1054 self.inner.chain()
1055 }
1056
1057 pub(super) fn amount_msats(&self) -> Option<u64> {
1058 self.inner.amount_msats().or_else(|| match self.inner.offer.amount() {
1059 Some(Amount::Bitcoin { amount_msats }) => {
1060 Some(amount_msats.saturating_mul(self.quantity().unwrap_or(1)))
1061 },
1062 Some(Amount::Currency { .. }) => None,
1063 None => {
1064 debug_assert!(false);
1065 None
1066 },
1067 })
1068 }
1069
1070 pub(super) fn has_amount_msats(&self) -> bool {
1071 self.inner.amount_msats().is_some()
1072 }
1073
1074 pub(super) fn features(&self) -> &InvoiceRequestFeatures {
1075 &self.inner.features
1076 }
1077
1078 pub(super) fn quantity(&self) -> Option<u64> {
1079 self.inner.quantity
1080 }
1081
1082 pub(super) fn payer_signing_pubkey(&self) -> PublicKey {
1083 self.payer_signing_pubkey
1084 }
1085
1086 pub(super) fn payer_note(&self) -> Option<PrintableString<'_>> {
1087 self.inner.payer_note.as_ref().map(|payer_note| PrintableString(payer_note.as_str()))
1088 }
1089
1090 pub(super) fn offer_from_hrn(&self) -> &Option<HumanReadableName> {
1091 &self.inner.offer_from_hrn
1092 }
1093
1094 pub(super) fn as_tlv_stream(&self) -> PartialInvoiceRequestTlvStreamRef<'_> {
1095 let (payer, offer, mut invoice_request, experimental_offer, experimental_invoice_request) =
1096 self.inner.as_tlv_stream();
1097 invoice_request.payer_id = Some(&self.payer_signing_pubkey);
1098 (payer, offer, invoice_request, experimental_offer, experimental_invoice_request)
1099 }
1100}
1101
1102impl InvoiceRequestContentsWithoutPayerSigningPubkey {
1103 pub(super) fn metadata(&self) -> &[u8] {
1104 self.payer.0.as_bytes().map(|bytes| bytes.as_slice()).unwrap_or(&[])
1105 }
1106
1107 pub(super) fn chain(&self) -> ChainHash {
1108 self.chain.unwrap_or_else(|| self.offer.implied_chain())
1109 }
1110
1111 pub(super) fn amount_msats(&self) -> Option<u64> {
1112 self.amount_msats
1113 }
1114
1115 pub(super) fn as_tlv_stream(&self) -> PartialInvoiceRequestTlvStreamRef<'_> {
1116 let payer = PayerTlvStreamRef { metadata: self.payer.0.as_bytes() };
1117
1118 let (offer, experimental_offer) = self.offer.as_tlv_stream();
1119
1120 let features = {
1121 if self.features == InvoiceRequestFeatures::empty() {
1122 None
1123 } else {
1124 Some(&self.features)
1125 }
1126 };
1127
1128 let invoice_request = InvoiceRequestTlvStreamRef {
1129 chain: self.chain.as_ref(),
1130 amount: self.amount_msats,
1131 features,
1132 quantity: self.quantity,
1133 payer_id: None,
1134 payer_note: self.payer_note.as_ref(),
1135 offer_from_hrn: self.offer_from_hrn.as_ref(),
1136 paths: None,
1137 };
1138
1139 let experimental_invoice_request = ExperimentalInvoiceRequestTlvStreamRef {
1140 #[cfg(test)]
1141 experimental_bar: self.experimental_bar,
1142 };
1143
1144 (payer, offer, invoice_request, experimental_offer, experimental_invoice_request)
1145 }
1146}
1147
1148impl Writeable for UnsignedInvoiceRequest {
1149 fn write<W: Writer>(&self, writer: &mut W) -> Result<(), io::Error> {
1150 WithoutLength(&self.bytes).write(writer)
1151 }
1152}
1153
1154impl Writeable for InvoiceRequest {
1155 fn write<W: Writer>(&self, writer: &mut W) -> Result<(), io::Error> {
1156 WithoutLength(&self.bytes).write(writer)
1157 }
1158}
1159
1160impl Writeable for InvoiceRequestContents {
1161 fn write<W: Writer>(&self, writer: &mut W) -> Result<(), io::Error> {
1162 self.as_tlv_stream().write(writer)
1163 }
1164}
1165
1166impl LengthReadable for InvoiceRequest {
1167 fn read_from_fixed_length_buffer<R: LengthLimitedRead>(r: &mut R) -> Result<Self, DecodeError> {
1168 let bytes: WithoutLength<Vec<u8>> = LengthReadable::read_from_fixed_length_buffer(r)?;
1169 Self::try_from(bytes.0).map_err(|e| match e {
1170 Bolt12ParseError::Decode(e) => e,
1171 _ => DecodeError::InvalidValue,
1172 })
1173 }
1174}
1175
1176pub(super) const INVOICE_REQUEST_TYPES: core::ops::Range<u64> = 80..160;
1178
1179pub(super) const INVOICE_REQUEST_PAYER_ID_TYPE: u64 = 88;
1184
1185tlv_stream!(InvoiceRequestTlvStream, InvoiceRequestTlvStreamRef<'a>, INVOICE_REQUEST_TYPES, {
1188 (80, chain: ChainHash),
1189 (82, amount: (u64, HighZeroBytesDroppedBigSize)),
1190 (84, features: (InvoiceRequestFeatures, WithoutLength)),
1191 (86, quantity: (u64, HighZeroBytesDroppedBigSize)),
1192 (INVOICE_REQUEST_PAYER_ID_TYPE, payer_id: PublicKey),
1193 (89, payer_note: (String, WithoutLength)),
1194 (90, paths: (Vec<BlindedMessagePath>, WithoutLength)),
1196 (91, offer_from_hrn: HumanReadableName),
1197});
1198
1199pub(super) const EXPERIMENTAL_INVOICE_REQUEST_TYPES: core::ops::Range<u64> =
1201 2_000_000_000..3_000_000_000;
1202
1203#[cfg(not(test))]
1204tlv_stream!(
1205 ExperimentalInvoiceRequestTlvStream,
1206 ExperimentalInvoiceRequestTlvStreamRef,
1207 EXPERIMENTAL_INVOICE_REQUEST_TYPES,
1208 {
1209 }
1212);
1213
1214#[cfg(test)]
1215tlv_stream!(
1216 ExperimentalInvoiceRequestTlvStream, ExperimentalInvoiceRequestTlvStreamRef,
1217 EXPERIMENTAL_INVOICE_REQUEST_TYPES, {
1218 (2_999_999_999, experimental_bar: (u64, HighZeroBytesDroppedBigSize)),
1219 }
1220);
1221
1222type FullInvoiceRequestTlvStream = (
1223 PayerTlvStream,
1224 OfferTlvStream,
1225 InvoiceRequestTlvStream,
1226 SignatureTlvStream,
1227 ExperimentalOfferTlvStream,
1228 ExperimentalInvoiceRequestTlvStream,
1229);
1230
1231type FullInvoiceRequestTlvStreamRef<'a> = (
1232 PayerTlvStreamRef<'a>,
1233 OfferTlvStreamRef<'a>,
1234 InvoiceRequestTlvStreamRef<'a>,
1235 SignatureTlvStreamRef<'a>,
1236 ExperimentalOfferTlvStreamRef,
1237 ExperimentalInvoiceRequestTlvStreamRef,
1238);
1239
1240impl CursorReadable for FullInvoiceRequestTlvStream {
1241 fn read<R: AsRef<[u8]>>(r: &mut io::Cursor<R>) -> Result<Self, DecodeError> {
1242 let payer = CursorReadable::read(r)?;
1243 let offer = CursorReadable::read(r)?;
1244 let invoice_request = CursorReadable::read(r)?;
1245 let signature = CursorReadable::read(r)?;
1246 let experimental_offer = CursorReadable::read(r)?;
1247 let experimental_invoice_request = CursorReadable::read(r)?;
1248
1249 Ok((
1250 payer,
1251 offer,
1252 invoice_request,
1253 signature,
1254 experimental_offer,
1255 experimental_invoice_request,
1256 ))
1257 }
1258}
1259
1260type PartialInvoiceRequestTlvStream = (
1261 PayerTlvStream,
1262 OfferTlvStream,
1263 InvoiceRequestTlvStream,
1264 ExperimentalOfferTlvStream,
1265 ExperimentalInvoiceRequestTlvStream,
1266);
1267
1268type PartialInvoiceRequestTlvStreamRef<'a> = (
1269 PayerTlvStreamRef<'a>,
1270 OfferTlvStreamRef<'a>,
1271 InvoiceRequestTlvStreamRef<'a>,
1272 ExperimentalOfferTlvStreamRef,
1273 ExperimentalInvoiceRequestTlvStreamRef,
1274);
1275
1276impl TryFrom<Vec<u8>> for UnsignedInvoiceRequest {
1277 type Error = Bolt12ParseError;
1278
1279 fn try_from(bytes: Vec<u8>) -> Result<Self, Self::Error> {
1280 let invoice_request = ParsedMessage::<PartialInvoiceRequestTlvStream>::try_from(bytes)?;
1281 let ParsedMessage { mut bytes, tlv_stream } = invoice_request;
1282
1283 let contents = InvoiceRequestContents::try_from(tlv_stream)?;
1284 let tagged_hash = TaggedHash::from_valid_tlv_stream_bytes(SIGNATURE_TAG, &bytes);
1285
1286 let offset = TlvStream::new(&bytes)
1287 .range(0..INVOICE_REQUEST_TYPES.end)
1288 .last()
1289 .map_or(0, |last_record| last_record.end);
1290 let experimental_bytes = bytes.split_off(offset);
1291
1292 Ok(UnsignedInvoiceRequest { bytes, experimental_bytes, contents, tagged_hash })
1293 }
1294}
1295
1296impl TryFrom<Vec<u8>> for InvoiceRequest {
1297 type Error = Bolt12ParseError;
1298
1299 fn try_from(bytes: Vec<u8>) -> Result<Self, Self::Error> {
1300 let invoice_request = ParsedMessage::<FullInvoiceRequestTlvStream>::try_from(bytes)?;
1301 let ParsedMessage { bytes, tlv_stream } = invoice_request;
1302 let (
1303 payer_tlv_stream,
1304 offer_tlv_stream,
1305 invoice_request_tlv_stream,
1306 SignatureTlvStream { signature },
1307 experimental_offer_tlv_stream,
1308 experimental_invoice_request_tlv_stream,
1309 ) = tlv_stream;
1310 let contents = InvoiceRequestContents::try_from((
1311 payer_tlv_stream,
1312 offer_tlv_stream,
1313 invoice_request_tlv_stream,
1314 experimental_offer_tlv_stream,
1315 experimental_invoice_request_tlv_stream,
1316 ))?;
1317
1318 let signature = match signature {
1319 None => {
1320 return Err(Bolt12ParseError::InvalidSemantics(
1321 Bolt12SemanticError::MissingSignature,
1322 ))
1323 },
1324 Some(signature) => signature,
1325 };
1326 let message = TaggedHash::from_valid_tlv_stream_bytes(SIGNATURE_TAG, &bytes);
1327 merkle::verify_signature(&signature, &message, contents.payer_signing_pubkey)?;
1328
1329 Ok(InvoiceRequest { bytes, contents, signature })
1330 }
1331}
1332
1333impl TryFrom<PartialInvoiceRequestTlvStream> for InvoiceRequestContents {
1334 type Error = Bolt12SemanticError;
1335
1336 fn try_from(tlv_stream: PartialInvoiceRequestTlvStream) -> Result<Self, Self::Error> {
1337 let (
1338 PayerTlvStream { metadata },
1339 offer_tlv_stream,
1340 InvoiceRequestTlvStream {
1341 chain,
1342 amount,
1343 features,
1344 quantity,
1345 payer_id,
1346 payer_note,
1347 paths,
1348 offer_from_hrn,
1349 },
1350 experimental_offer_tlv_stream,
1351 ExperimentalInvoiceRequestTlvStream {
1352 #[cfg(test)]
1353 experimental_bar,
1354 },
1355 ) = tlv_stream;
1356
1357 let payer = match metadata {
1358 None => return Err(Bolt12SemanticError::MissingPayerMetadata),
1359 Some(metadata) => PayerContents(Metadata::Bytes(metadata)),
1360 };
1361 let offer = OfferContents::try_from((offer_tlv_stream, experimental_offer_tlv_stream))?;
1362
1363 if !offer.supports_chain(chain.unwrap_or_else(|| offer.implied_chain())) {
1364 return Err(Bolt12SemanticError::UnsupportedChain);
1365 }
1366
1367 if offer.amount().is_none() && amount.is_none() {
1368 return Err(Bolt12SemanticError::MissingAmount);
1369 }
1370
1371 offer.check_quantity(quantity)?;
1372 offer.check_amount_msats_for_quantity(amount, quantity)?;
1373
1374 let features = features.unwrap_or_else(InvoiceRequestFeatures::empty);
1375
1376 let payer_signing_pubkey = match payer_id {
1377 None => return Err(Bolt12SemanticError::MissingPayerSigningPubkey),
1378 Some(payer_id) => payer_id,
1379 };
1380
1381 if paths.is_some() {
1382 return Err(Bolt12SemanticError::UnexpectedPaths);
1383 }
1384
1385 Ok(InvoiceRequestContents {
1386 inner: InvoiceRequestContentsWithoutPayerSigningPubkey {
1387 payer,
1388 offer,
1389 chain,
1390 amount_msats: amount,
1391 features,
1392 quantity,
1393 payer_note,
1394 offer_from_hrn,
1395 #[cfg(test)]
1396 experimental_bar,
1397 },
1398 payer_signing_pubkey,
1399 })
1400 }
1401}
1402
1403#[derive(Clone, Debug, Eq, PartialEq)]
1407pub struct InvoiceRequestFields {
1408 pub payer_signing_pubkey: PublicKey,
1410
1411 pub quantity: Option<u64>,
1413
1414 pub payer_note_truncated: Option<UntrustedString>,
1417
1418 pub human_readable_name: Option<HumanReadableName>,
1420}
1421
1422#[cfg(not(fuzzing))]
1424pub const PAYER_NOTE_LIMIT: usize = 512;
1425
1426#[cfg(fuzzing)]
1428pub const PAYER_NOTE_LIMIT: usize = 8;
1429
1430impl Writeable for InvoiceRequestFields {
1431 fn write<W: Writer>(&self, writer: &mut W) -> Result<(), io::Error> {
1432 write_tlv_fields!(writer, {
1433 (0, self.payer_signing_pubkey, required),
1434 (1, self.human_readable_name, option),
1435 (2, self.quantity.map(|v| HighZeroBytesDroppedBigSize(v)), option),
1436 (4, self.payer_note_truncated.as_ref().map(|s| WithoutLength(&s.0)), option),
1437 });
1438 Ok(())
1439 }
1440}
1441
1442impl Readable for InvoiceRequestFields {
1443 fn read<R: io::Read>(reader: &mut R) -> Result<Self, DecodeError> {
1444 _init_and_read_len_prefixed_tlv_fields!(reader, {
1445 (0, payer_signing_pubkey, required),
1446 (1, human_readable_name, option),
1447 (2, quantity, (option, encoding: (u64, HighZeroBytesDroppedBigSize))),
1448 (4, payer_note_truncated, (option, encoding: (String, WithoutLength))),
1449 });
1450
1451 Ok(InvoiceRequestFields {
1452 payer_signing_pubkey: payer_signing_pubkey.0.unwrap(),
1453 quantity,
1454 payer_note_truncated: payer_note_truncated.map(|s| UntrustedString(s)),
1455 human_readable_name,
1456 })
1457 }
1458}
1459
1460#[cfg(test)]
1461mod tests {
1462 use super::{
1463 ExperimentalInvoiceRequestTlvStreamRef, InvoiceRequest, InvoiceRequestFields,
1464 InvoiceRequestTlvStreamRef, UnsignedInvoiceRequest, EXPERIMENTAL_INVOICE_REQUEST_TYPES,
1465 INVOICE_REQUEST_TYPES, PAYER_NOTE_LIMIT, SIGNATURE_TAG,
1466 };
1467
1468 use crate::ln::channelmanager::PaymentId;
1469 use crate::ln::inbound_payment::ExpandedKey;
1470 use crate::ln::msgs::{DecodeError, MAX_VALUE_MSAT};
1471 use crate::offers::invoice::{Bolt12Invoice, SIGNATURE_TAG as INVOICE_SIGNATURE_TAG};
1472 use crate::offers::invoice_request::string_truncate_safe;
1473 use crate::offers::merkle::{self, SignatureTlvStreamRef, TaggedHash, TlvStream};
1474 use crate::offers::nonce::Nonce;
1475 #[cfg(not(c_bindings))]
1476 use crate::offers::offer::OfferBuilder;
1477 #[cfg(c_bindings)]
1478 use crate::offers::offer::OfferWithExplicitMetadataBuilder as OfferBuilder;
1479 use crate::offers::offer::{
1480 Amount, CurrencyCode, ExperimentalOfferTlvStreamRef, OfferTlvStreamRef, Quantity,
1481 };
1482 use crate::offers::parse::{Bolt12ParseError, Bolt12SemanticError};
1483 use crate::offers::payer::PayerTlvStreamRef;
1484 use crate::offers::test_utils::*;
1485 use crate::types::features::{InvoiceRequestFeatures, OfferFeatures};
1486 use crate::types::string::{PrintableString, UntrustedString};
1487 use crate::util::ser::{BigSize, Readable, Writeable};
1488 use bitcoin::constants::ChainHash;
1489 use bitcoin::network::Network;
1490 use bitcoin::secp256k1::{self, Keypair, Secp256k1, SecretKey};
1491 use core::num::NonZeroU64;
1492 #[cfg(feature = "std")]
1493 use core::time::Duration;
1494
1495 #[test]
1496 fn builds_invoice_request_with_defaults() {
1497 let expanded_key = ExpandedKey::new([42; 32]);
1498 let entropy = FixedEntropy {};
1499 let nonce = Nonce::from_entropy_source(&entropy);
1500 let secp_ctx = Secp256k1::new();
1501 let payment_id = PaymentId([1; 32]);
1502 let encrypted_payment_id = expanded_key.crypt_for_offer(payment_id.0, nonce);
1503
1504 let invoice_request = OfferBuilder::new(recipient_pubkey())
1505 .amount_msats(1000)
1506 .build()
1507 .unwrap()
1508 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1509 .unwrap()
1510 .build_and_sign()
1511 .unwrap();
1512
1513 let mut buffer = Vec::new();
1514 invoice_request.write(&mut buffer).unwrap();
1515
1516 assert_eq!(invoice_request.bytes, buffer.as_slice());
1517 assert_eq!(invoice_request.payer_metadata(), &encrypted_payment_id);
1518 assert_eq!(
1519 invoice_request.chains(),
1520 vec![ChainHash::using_genesis_block(Network::Bitcoin)]
1521 );
1522 assert_eq!(invoice_request.metadata(), None);
1523 assert_eq!(invoice_request.amount(), Some(Amount::Bitcoin { amount_msats: 1000 }));
1524 assert_eq!(invoice_request.description(), Some(PrintableString("")));
1525 assert_eq!(invoice_request.offer_features(), &OfferFeatures::empty());
1526 assert_eq!(invoice_request.absolute_expiry(), None);
1527 assert_eq!(invoice_request.paths(), &[]);
1528 assert_eq!(invoice_request.issuer(), None);
1529 assert_eq!(invoice_request.supported_quantity(), Quantity::One);
1530 assert_eq!(invoice_request.issuer_signing_pubkey(), Some(recipient_pubkey()));
1531 assert_eq!(invoice_request.chain(), ChainHash::using_genesis_block(Network::Bitcoin));
1532 assert_eq!(invoice_request.amount_msats(), Some(1000));
1533 assert_eq!(invoice_request.invoice_request_features(), &InvoiceRequestFeatures::empty());
1534 assert_eq!(invoice_request.quantity(), None);
1535 assert_eq!(invoice_request.payer_note(), None);
1536
1537 let message =
1538 TaggedHash::from_valid_tlv_stream_bytes(SIGNATURE_TAG, &invoice_request.bytes);
1539 assert!(merkle::verify_signature(
1540 &invoice_request.signature,
1541 &message,
1542 invoice_request.payer_signing_pubkey(),
1543 )
1544 .is_ok());
1545
1546 assert_eq!(
1547 invoice_request.as_tlv_stream(),
1548 (
1549 PayerTlvStreamRef { metadata: Some(&encrypted_payment_id.to_vec()) },
1550 OfferTlvStreamRef {
1551 chains: None,
1552 metadata: None,
1553 currency: None,
1554 amount: Some(1000),
1555 description: Some(&String::from("")),
1556 features: None,
1557 absolute_expiry: None,
1558 paths: None,
1559 issuer: None,
1560 quantity_max: None,
1561 issuer_id: Some(&recipient_pubkey()),
1562 },
1563 InvoiceRequestTlvStreamRef {
1564 chain: None,
1565 amount: None,
1566 features: None,
1567 quantity: None,
1568 payer_id: Some(&invoice_request.payer_signing_pubkey()),
1569 payer_note: None,
1570 paths: None,
1571 offer_from_hrn: None,
1572 },
1573 SignatureTlvStreamRef { signature: Some(&invoice_request.signature()) },
1574 ExperimentalOfferTlvStreamRef { experimental_foo: None },
1575 ExperimentalInvoiceRequestTlvStreamRef { experimental_bar: None },
1576 ),
1577 );
1578
1579 if let Err(e) = InvoiceRequest::try_from(buffer) {
1580 panic!("error parsing invoice request: {:?}", e);
1581 }
1582 }
1583
1584 #[cfg(feature = "std")]
1585 #[test]
1586 fn builds_invoice_request_from_offer_with_expiration() {
1587 let expanded_key = ExpandedKey::new([42; 32]);
1588 let entropy = FixedEntropy {};
1589 let nonce = Nonce::from_entropy_source(&entropy);
1590 let secp_ctx = Secp256k1::new();
1591 let payment_id = PaymentId([1; 32]);
1592
1593 let future_expiry = Duration::from_secs(u64::max_value());
1594 let past_expiry = Duration::from_secs(0);
1595
1596 if let Err(e) = OfferBuilder::new(recipient_pubkey())
1597 .amount_msats(1000)
1598 .absolute_expiry(future_expiry)
1599 .build()
1600 .unwrap()
1601 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1602 .unwrap()
1603 .build_and_sign()
1604 {
1605 panic!("error building invoice_request: {:?}", e);
1606 }
1607
1608 match OfferBuilder::new(recipient_pubkey())
1609 .amount_msats(1000)
1610 .absolute_expiry(past_expiry)
1611 .build()
1612 .unwrap()
1613 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1614 .unwrap()
1615 .build_and_sign()
1616 {
1617 Ok(_) => panic!("expected error"),
1618 Err(e) => assert_eq!(e, Bolt12SemanticError::AlreadyExpired),
1619 }
1620 }
1621
1622 #[test]
1623 fn builds_invoice_request_with_derived_payer_signing_pubkey() {
1624 let expanded_key = ExpandedKey::new([42; 32]);
1625 let entropy = FixedEntropy {};
1626 let nonce = Nonce::from_entropy_source(&entropy);
1627 let secp_ctx = Secp256k1::new();
1628 let payment_id = PaymentId([1; 32]);
1629
1630 let offer = OfferBuilder::new(recipient_pubkey())
1631 .amount_msats(1000)
1632 .experimental_foo(42)
1633 .build()
1634 .unwrap();
1635 let invoice_request = offer
1636 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1637 .unwrap()
1638 .experimental_bar(42)
1639 .build_and_sign()
1640 .unwrap();
1641
1642 let invoice = invoice_request
1643 .respond_with_no_std(payment_paths(), payment_hash(), now())
1644 .unwrap()
1645 .experimental_baz(42)
1646 .build()
1647 .unwrap()
1648 .sign(recipient_sign)
1649 .unwrap();
1650 assert!(invoice.verify_using_metadata(&expanded_key, &secp_ctx).is_err());
1651 assert!(invoice
1652 .verify_using_payer_data(payment_id, nonce, &expanded_key, &secp_ctx)
1653 .is_ok());
1654
1655 let (
1657 payer_tlv_stream,
1658 offer_tlv_stream,
1659 mut invoice_request_tlv_stream,
1660 mut invoice_tlv_stream,
1661 mut signature_tlv_stream,
1662 experimental_offer_tlv_stream,
1663 experimental_invoice_request_tlv_stream,
1664 experimental_invoice_tlv_stream,
1665 ) = invoice.as_tlv_stream();
1666 invoice_request_tlv_stream.amount = Some(2000);
1667 invoice_tlv_stream.amount = Some(2000);
1668
1669 let tlv_stream =
1670 (payer_tlv_stream, offer_tlv_stream, invoice_request_tlv_stream, invoice_tlv_stream);
1671 let experimental_tlv_stream = (
1672 experimental_offer_tlv_stream,
1673 experimental_invoice_request_tlv_stream,
1674 experimental_invoice_tlv_stream,
1675 );
1676 let mut bytes = Vec::new();
1677 (&tlv_stream, &experimental_tlv_stream).write(&mut bytes).unwrap();
1678
1679 let message = TaggedHash::from_valid_tlv_stream_bytes(INVOICE_SIGNATURE_TAG, &bytes);
1680 let signature = merkle::sign_message(recipient_sign, &message, recipient_pubkey()).unwrap();
1681 signature_tlv_stream.signature = Some(&signature);
1682
1683 let mut encoded_invoice = Vec::new();
1684 (tlv_stream, signature_tlv_stream, experimental_tlv_stream)
1685 .write(&mut encoded_invoice)
1686 .unwrap();
1687
1688 let invoice = Bolt12Invoice::try_from(encoded_invoice).unwrap();
1689 assert!(invoice
1690 .verify_using_payer_data(payment_id, nonce, &expanded_key, &secp_ctx)
1691 .is_err());
1692
1693 let (
1695 payer_tlv_stream,
1696 offer_tlv_stream,
1697 mut invoice_request_tlv_stream,
1698 invoice_tlv_stream,
1699 mut signature_tlv_stream,
1700 experimental_offer_tlv_stream,
1701 experimental_invoice_request_tlv_stream,
1702 experimental_invoice_tlv_stream,
1703 ) = invoice.as_tlv_stream();
1704 let payer_id = pubkey(1);
1705 invoice_request_tlv_stream.payer_id = Some(&payer_id);
1706
1707 let tlv_stream =
1708 (payer_tlv_stream, offer_tlv_stream, invoice_request_tlv_stream, invoice_tlv_stream);
1709 let experimental_tlv_stream = (
1710 experimental_offer_tlv_stream,
1711 experimental_invoice_request_tlv_stream,
1712 experimental_invoice_tlv_stream,
1713 );
1714 let mut bytes = Vec::new();
1715 (&tlv_stream, &experimental_tlv_stream).write(&mut bytes).unwrap();
1716
1717 let message = TaggedHash::from_valid_tlv_stream_bytes(INVOICE_SIGNATURE_TAG, &bytes);
1718 let signature = merkle::sign_message(recipient_sign, &message, recipient_pubkey()).unwrap();
1719 signature_tlv_stream.signature = Some(&signature);
1720
1721 let mut encoded_invoice = Vec::new();
1722 (tlv_stream, signature_tlv_stream, experimental_tlv_stream)
1723 .write(&mut encoded_invoice)
1724 .unwrap();
1725
1726 let invoice = Bolt12Invoice::try_from(encoded_invoice).unwrap();
1727 assert!(invoice
1728 .verify_using_payer_data(payment_id, nonce, &expanded_key, &secp_ctx)
1729 .is_err());
1730 }
1731
1732 #[test]
1733 fn builds_invoice_request_with_chain() {
1734 let expanded_key = ExpandedKey::new([42; 32]);
1735 let entropy = FixedEntropy {};
1736 let nonce = Nonce::from_entropy_source(&entropy);
1737 let secp_ctx = Secp256k1::new();
1738 let payment_id = PaymentId([1; 32]);
1739
1740 let mainnet = ChainHash::using_genesis_block(Network::Bitcoin);
1741 let testnet = ChainHash::using_genesis_block(Network::Testnet);
1742
1743 let invoice_request = OfferBuilder::new(recipient_pubkey())
1744 .amount_msats(1000)
1745 .build()
1746 .unwrap()
1747 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1748 .unwrap()
1749 .chain(Network::Bitcoin)
1750 .unwrap()
1751 .build_and_sign()
1752 .unwrap();
1753 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1754 assert_eq!(invoice_request.chain(), mainnet);
1755 assert_eq!(tlv_stream.chain, None);
1756
1757 let invoice_request = OfferBuilder::new(recipient_pubkey())
1758 .amount_msats(1000)
1759 .chain(Network::Testnet)
1760 .build()
1761 .unwrap()
1762 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1763 .unwrap()
1764 .chain(Network::Testnet)
1765 .unwrap()
1766 .build_and_sign()
1767 .unwrap();
1768 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1769 assert_eq!(invoice_request.chain(), testnet);
1770 assert_eq!(tlv_stream.chain, Some(&testnet));
1771
1772 let invoice_request = OfferBuilder::new(recipient_pubkey())
1773 .amount_msats(1000)
1774 .chain(Network::Bitcoin)
1775 .chain(Network::Testnet)
1776 .build()
1777 .unwrap()
1778 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1779 .unwrap()
1780 .chain(Network::Bitcoin)
1781 .unwrap()
1782 .build_and_sign()
1783 .unwrap();
1784 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1785 assert_eq!(invoice_request.chain(), mainnet);
1786 assert_eq!(tlv_stream.chain, None);
1787
1788 let invoice_request = OfferBuilder::new(recipient_pubkey())
1789 .amount_msats(1000)
1790 .chain(Network::Bitcoin)
1791 .chain(Network::Testnet)
1792 .build()
1793 .unwrap()
1794 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1795 .unwrap()
1796 .chain(Network::Bitcoin)
1797 .unwrap()
1798 .chain(Network::Testnet)
1799 .unwrap()
1800 .build_and_sign()
1801 .unwrap();
1802 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1803 assert_eq!(invoice_request.chain(), testnet);
1804 assert_eq!(tlv_stream.chain, Some(&testnet));
1805
1806 match OfferBuilder::new(recipient_pubkey())
1807 .amount_msats(1000)
1808 .chain(Network::Testnet)
1809 .build()
1810 .unwrap()
1811 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1812 .unwrap()
1813 .chain(Network::Bitcoin)
1814 {
1815 Ok(_) => panic!("expected error"),
1816 Err(e) => assert_eq!(e, Bolt12SemanticError::UnsupportedChain),
1817 }
1818
1819 match OfferBuilder::new(recipient_pubkey())
1820 .amount_msats(1000)
1821 .chain(Network::Testnet)
1822 .build()
1823 .unwrap()
1824 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1825 .unwrap()
1826 .build_and_sign()
1827 {
1828 Ok(_) => panic!("expected error"),
1829 Err(e) => assert_eq!(e, Bolt12SemanticError::UnsupportedChain),
1830 }
1831 }
1832
1833 #[test]
1834 fn builds_invoice_request_with_amount() {
1835 let expanded_key = ExpandedKey::new([42; 32]);
1836 let entropy = FixedEntropy {};
1837 let nonce = Nonce::from_entropy_source(&entropy);
1838 let secp_ctx = Secp256k1::new();
1839 let payment_id = PaymentId([1; 32]);
1840
1841 let invoice_request = OfferBuilder::new(recipient_pubkey())
1842 .amount_msats(1000)
1843 .build()
1844 .unwrap()
1845 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1846 .unwrap()
1847 .amount_msats(1000)
1848 .unwrap()
1849 .build_and_sign()
1850 .unwrap();
1851 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1852 assert!(invoice_request.has_amount_msats());
1853 assert_eq!(invoice_request.amount_msats(), Some(1000));
1854 assert_eq!(tlv_stream.amount, Some(1000));
1855
1856 let invoice_request = OfferBuilder::new(recipient_pubkey())
1857 .amount_msats(1000)
1858 .build()
1859 .unwrap()
1860 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1861 .unwrap()
1862 .amount_msats(1001)
1863 .unwrap()
1864 .amount_msats(1000)
1865 .unwrap()
1866 .build_and_sign()
1867 .unwrap();
1868 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1869 assert!(invoice_request.has_amount_msats());
1870 assert_eq!(invoice_request.amount_msats(), Some(1000));
1871 assert_eq!(tlv_stream.amount, Some(1000));
1872
1873 let invoice_request = OfferBuilder::new(recipient_pubkey())
1874 .amount_msats(1000)
1875 .build()
1876 .unwrap()
1877 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1878 .unwrap()
1879 .amount_msats(1001)
1880 .unwrap()
1881 .build_and_sign()
1882 .unwrap();
1883 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1884 assert!(invoice_request.has_amount_msats());
1885 assert_eq!(invoice_request.amount_msats(), Some(1001));
1886 assert_eq!(tlv_stream.amount, Some(1001));
1887
1888 match OfferBuilder::new(recipient_pubkey())
1889 .amount_msats(1000)
1890 .build()
1891 .unwrap()
1892 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1893 .unwrap()
1894 .amount_msats(999)
1895 {
1896 Ok(_) => panic!("expected error"),
1897 Err(e) => assert_eq!(e, Bolt12SemanticError::InsufficientAmount),
1898 }
1899
1900 match OfferBuilder::new(recipient_pubkey())
1901 .amount_msats(1000)
1902 .supported_quantity(Quantity::Unbounded)
1903 .build()
1904 .unwrap()
1905 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1906 .unwrap()
1907 .quantity(2)
1908 .unwrap()
1909 .amount_msats(1000)
1910 {
1911 Ok(_) => panic!("expected error"),
1912 Err(e) => assert_eq!(e, Bolt12SemanticError::InsufficientAmount),
1913 }
1914
1915 match OfferBuilder::new(recipient_pubkey())
1916 .amount_msats(1000)
1917 .build()
1918 .unwrap()
1919 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1920 .unwrap()
1921 .amount_msats(MAX_VALUE_MSAT + 1)
1922 {
1923 Ok(_) => panic!("expected error"),
1924 Err(e) => assert_eq!(e, Bolt12SemanticError::InvalidAmount),
1925 }
1926
1927 match OfferBuilder::new(recipient_pubkey())
1928 .amount_msats(1000)
1929 .supported_quantity(Quantity::Unbounded)
1930 .build()
1931 .unwrap()
1932 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1933 .unwrap()
1934 .amount_msats(1000)
1935 .unwrap()
1936 .quantity(2)
1937 .unwrap()
1938 .build_and_sign()
1939 {
1940 Ok(_) => panic!("expected error"),
1941 Err(e) => assert_eq!(e, Bolt12SemanticError::InsufficientAmount),
1942 }
1943
1944 match OfferBuilder::new(recipient_pubkey())
1945 .build()
1946 .unwrap()
1947 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1948 .unwrap()
1949 .build_and_sign()
1950 {
1951 Ok(_) => panic!("expected error"),
1952 Err(e) => assert_eq!(e, Bolt12SemanticError::MissingAmount),
1953 }
1954
1955 match OfferBuilder::new(recipient_pubkey())
1956 .amount_msats(1000)
1957 .supported_quantity(Quantity::Unbounded)
1958 .build()
1959 .unwrap()
1960 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1961 .unwrap()
1962 .quantity(u64::max_value())
1963 .unwrap()
1964 .build_and_sign()
1965 {
1966 Ok(_) => panic!("expected error"),
1967 Err(e) => assert_eq!(e, Bolt12SemanticError::InvalidAmount),
1968 }
1969 }
1970
1971 #[test]
1972 fn builds_invoice_request_without_amount() {
1973 let expanded_key = ExpandedKey::new([42; 32]);
1974 let entropy = FixedEntropy {};
1975 let nonce = Nonce::from_entropy_source(&entropy);
1976 let secp_ctx = Secp256k1::new();
1977 let payment_id = PaymentId([1; 32]);
1978
1979 let invoice_request = OfferBuilder::new(recipient_pubkey())
1980 .amount_msats(1000)
1981 .build()
1982 .unwrap()
1983 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1984 .unwrap()
1985 .build_and_sign()
1986 .unwrap();
1987 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
1988 assert!(!invoice_request.has_amount_msats());
1989 assert_eq!(invoice_request.amount_msats(), Some(1000));
1990 assert_eq!(tlv_stream.amount, None);
1991
1992 let invoice_request = OfferBuilder::new(recipient_pubkey())
1993 .amount_msats(1000)
1994 .supported_quantity(Quantity::Unbounded)
1995 .build()
1996 .unwrap()
1997 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
1998 .unwrap()
1999 .quantity(2)
2000 .unwrap()
2001 .build_and_sign()
2002 .unwrap();
2003 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2004 assert!(!invoice_request.has_amount_msats());
2005 assert_eq!(invoice_request.amount_msats(), Some(2000));
2006 assert_eq!(tlv_stream.amount, None);
2007
2008 let invoice_request = OfferBuilder::new(recipient_pubkey())
2009 .amount(Amount::Currency {
2010 iso4217_code: CurrencyCode::new(*b"USD").unwrap(),
2011 amount: 10,
2012 })
2013 .build_unchecked()
2014 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2015 .unwrap()
2016 .build_unchecked_and_sign();
2017 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2018 assert!(!invoice_request.has_amount_msats());
2019 assert_eq!(invoice_request.amount_msats(), None);
2020 assert_eq!(tlv_stream.amount, None);
2021 }
2022
2023 #[test]
2024 fn builds_invoice_request_with_features() {
2025 let expanded_key = ExpandedKey::new([42; 32]);
2026 let entropy = FixedEntropy {};
2027 let nonce = Nonce::from_entropy_source(&entropy);
2028 let secp_ctx = Secp256k1::new();
2029 let payment_id = PaymentId([1; 32]);
2030
2031 let invoice_request = OfferBuilder::new(recipient_pubkey())
2032 .amount_msats(1000)
2033 .build()
2034 .unwrap()
2035 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2036 .unwrap()
2037 .features_unchecked(InvoiceRequestFeatures::unknown())
2038 .build_and_sign()
2039 .unwrap();
2040 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2041 assert_eq!(invoice_request.invoice_request_features(), &InvoiceRequestFeatures::unknown());
2042 assert_eq!(tlv_stream.features, Some(&InvoiceRequestFeatures::unknown()));
2043
2044 let invoice_request = OfferBuilder::new(recipient_pubkey())
2045 .amount_msats(1000)
2046 .build()
2047 .unwrap()
2048 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2049 .unwrap()
2050 .features_unchecked(InvoiceRequestFeatures::unknown())
2051 .features_unchecked(InvoiceRequestFeatures::empty())
2052 .build_and_sign()
2053 .unwrap();
2054 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2055 assert_eq!(invoice_request.invoice_request_features(), &InvoiceRequestFeatures::empty());
2056 assert_eq!(tlv_stream.features, None);
2057 }
2058
2059 #[test]
2060 fn builds_invoice_request_with_quantity() {
2061 let expanded_key = ExpandedKey::new([42; 32]);
2062 let entropy = FixedEntropy {};
2063 let nonce = Nonce::from_entropy_source(&entropy);
2064 let secp_ctx = Secp256k1::new();
2065 let payment_id = PaymentId([1; 32]);
2066
2067 let one = NonZeroU64::new(1).unwrap();
2068 let ten = NonZeroU64::new(10).unwrap();
2069
2070 let invoice_request = OfferBuilder::new(recipient_pubkey())
2071 .amount_msats(1000)
2072 .supported_quantity(Quantity::One)
2073 .build()
2074 .unwrap()
2075 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2076 .unwrap()
2077 .build_and_sign()
2078 .unwrap();
2079 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2080 assert_eq!(invoice_request.quantity(), None);
2081 assert_eq!(tlv_stream.quantity, None);
2082
2083 match OfferBuilder::new(recipient_pubkey())
2084 .amount_msats(1000)
2085 .supported_quantity(Quantity::One)
2086 .build()
2087 .unwrap()
2088 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2089 .unwrap()
2090 .amount_msats(2_000)
2091 .unwrap()
2092 .quantity(2)
2093 {
2094 Ok(_) => panic!("expected error"),
2095 Err(e) => assert_eq!(e, Bolt12SemanticError::UnexpectedQuantity),
2096 }
2097
2098 let invoice_request = OfferBuilder::new(recipient_pubkey())
2099 .amount_msats(1000)
2100 .supported_quantity(Quantity::Bounded(ten))
2101 .build()
2102 .unwrap()
2103 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2104 .unwrap()
2105 .amount_msats(10_000)
2106 .unwrap()
2107 .quantity(10)
2108 .unwrap()
2109 .build_and_sign()
2110 .unwrap();
2111 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2112 assert_eq!(invoice_request.amount_msats(), Some(10_000));
2113 assert_eq!(tlv_stream.amount, Some(10_000));
2114
2115 match OfferBuilder::new(recipient_pubkey())
2116 .amount_msats(1000)
2117 .supported_quantity(Quantity::Bounded(ten))
2118 .build()
2119 .unwrap()
2120 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2121 .unwrap()
2122 .amount_msats(11_000)
2123 .unwrap()
2124 .quantity(11)
2125 {
2126 Ok(_) => panic!("expected error"),
2127 Err(e) => assert_eq!(e, Bolt12SemanticError::InvalidQuantity),
2128 }
2129
2130 match OfferBuilder::new(recipient_pubkey())
2131 .amount_msats(1000)
2132 .supported_quantity(Quantity::Bounded(ten))
2133 .build()
2134 .unwrap()
2135 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2136 .unwrap()
2137 .quantity(0)
2138 {
2139 Ok(_) => panic!("expected error"),
2140 Err(e) => assert_eq!(e, Bolt12SemanticError::InvalidQuantity),
2141 }
2142
2143 let invoice_request = OfferBuilder::new(recipient_pubkey())
2144 .amount_msats(1000)
2145 .supported_quantity(Quantity::Unbounded)
2146 .build()
2147 .unwrap()
2148 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2149 .unwrap()
2150 .amount_msats(2_000)
2151 .unwrap()
2152 .quantity(2)
2153 .unwrap()
2154 .build_and_sign()
2155 .unwrap();
2156 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2157 assert_eq!(invoice_request.amount_msats(), Some(2_000));
2158 assert_eq!(tlv_stream.amount, Some(2_000));
2159
2160 match OfferBuilder::new(recipient_pubkey())
2161 .amount_msats(1000)
2162 .supported_quantity(Quantity::Unbounded)
2163 .build()
2164 .unwrap()
2165 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2166 .unwrap()
2167 .build_and_sign()
2168 {
2169 Ok(_) => panic!("expected error"),
2170 Err(e) => assert_eq!(e, Bolt12SemanticError::MissingQuantity),
2171 }
2172
2173 match OfferBuilder::new(recipient_pubkey())
2174 .amount_msats(1000)
2175 .supported_quantity(Quantity::Bounded(one))
2176 .build()
2177 .unwrap()
2178 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2179 .unwrap()
2180 .build_and_sign()
2181 {
2182 Ok(_) => panic!("expected error"),
2183 Err(e) => assert_eq!(e, Bolt12SemanticError::MissingQuantity),
2184 }
2185 }
2186
2187 #[test]
2188 fn builds_invoice_request_with_payer_note() {
2189 let expanded_key = ExpandedKey::new([42; 32]);
2190 let entropy = FixedEntropy {};
2191 let nonce = Nonce::from_entropy_source(&entropy);
2192 let secp_ctx = Secp256k1::new();
2193 let payment_id = PaymentId([1; 32]);
2194
2195 let invoice_request = OfferBuilder::new(recipient_pubkey())
2196 .amount_msats(1000)
2197 .build()
2198 .unwrap()
2199 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2200 .unwrap()
2201 .payer_note("bar".into())
2202 .build_and_sign()
2203 .unwrap();
2204 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2205 assert_eq!(invoice_request.payer_note(), Some(PrintableString("bar")));
2206 assert_eq!(tlv_stream.payer_note, Some(&String::from("bar")));
2207
2208 let invoice_request = OfferBuilder::new(recipient_pubkey())
2209 .amount_msats(1000)
2210 .build()
2211 .unwrap()
2212 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2213 .unwrap()
2214 .payer_note("bar".into())
2215 .payer_note("baz".into())
2216 .build_and_sign()
2217 .unwrap();
2218 let (_, _, tlv_stream, _, _, _) = invoice_request.as_tlv_stream();
2219 assert_eq!(invoice_request.payer_note(), Some(PrintableString("baz")));
2220 assert_eq!(tlv_stream.payer_note, Some(&String::from("baz")));
2221 }
2222
2223 #[test]
2224 fn fails_responding_with_unknown_required_features() {
2225 let expanded_key = ExpandedKey::new([42; 32]);
2226 let entropy = FixedEntropy {};
2227 let nonce = Nonce::from_entropy_source(&entropy);
2228 let secp_ctx = Secp256k1::new();
2229 let payment_id = PaymentId([1; 32]);
2230
2231 match OfferBuilder::new(recipient_pubkey())
2232 .amount_msats(1000)
2233 .build()
2234 .unwrap()
2235 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2236 .unwrap()
2237 .features_unchecked(InvoiceRequestFeatures::unknown())
2238 .build_and_sign()
2239 .unwrap()
2240 .respond_with_no_std(payment_paths(), payment_hash(), now())
2241 {
2242 Ok(_) => panic!("expected error"),
2243 Err(e) => assert_eq!(e, Bolt12SemanticError::UnknownRequiredFeatures),
2244 }
2245 }
2246
2247 #[test]
2248 fn parses_invoice_request_with_metadata() {
2249 let expanded_key = ExpandedKey::new([42; 32]);
2250 let entropy = FixedEntropy {};
2251 let nonce = Nonce::from_entropy_source(&entropy);
2252 let secp_ctx = Secp256k1::new();
2253 let payment_id = PaymentId([1; 32]);
2254
2255 let invoice_request = OfferBuilder::new(recipient_pubkey())
2256 .amount_msats(1000)
2257 .build()
2258 .unwrap()
2259 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2260 .unwrap()
2261 .build_and_sign()
2262 .unwrap();
2263
2264 let mut buffer = Vec::new();
2265 invoice_request.write(&mut buffer).unwrap();
2266
2267 if let Err(e) = InvoiceRequest::try_from(buffer) {
2268 panic!("error parsing invoice_request: {:?}", e);
2269 }
2270 }
2271
2272 #[test]
2273 fn parses_invoice_request_with_chain() {
2274 let expanded_key = ExpandedKey::new([42; 32]);
2275 let entropy = FixedEntropy {};
2276 let nonce = Nonce::from_entropy_source(&entropy);
2277 let secp_ctx = Secp256k1::new();
2278 let payment_id = PaymentId([1; 32]);
2279
2280 let invoice_request = OfferBuilder::new(recipient_pubkey())
2281 .amount_msats(1000)
2282 .build()
2283 .unwrap()
2284 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2285 .unwrap()
2286 .chain(Network::Bitcoin)
2287 .unwrap()
2288 .build_and_sign()
2289 .unwrap();
2290
2291 let mut buffer = Vec::new();
2292 invoice_request.write(&mut buffer).unwrap();
2293
2294 if let Err(e) = InvoiceRequest::try_from(buffer) {
2295 panic!("error parsing invoice_request: {:?}", e);
2296 }
2297
2298 let invoice_request = OfferBuilder::new(recipient_pubkey())
2299 .amount_msats(1000)
2300 .build()
2301 .unwrap()
2302 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2303 .unwrap()
2304 .chain_unchecked(Network::Testnet)
2305 .build_unchecked_and_sign();
2306
2307 let mut buffer = Vec::new();
2308 invoice_request.write(&mut buffer).unwrap();
2309
2310 match InvoiceRequest::try_from(buffer) {
2311 Ok(_) => panic!("expected error"),
2312 Err(e) => assert_eq!(
2313 e,
2314 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::UnsupportedChain)
2315 ),
2316 }
2317 }
2318
2319 #[test]
2320 fn parses_invoice_request_with_amount() {
2321 let expanded_key = ExpandedKey::new([42; 32]);
2322 let entropy = FixedEntropy {};
2323 let nonce = Nonce::from_entropy_source(&entropy);
2324 let secp_ctx = Secp256k1::new();
2325 let payment_id = PaymentId([1; 32]);
2326
2327 let invoice_request = OfferBuilder::new(recipient_pubkey())
2328 .amount_msats(1000)
2329 .build()
2330 .unwrap()
2331 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2332 .unwrap()
2333 .build_and_sign()
2334 .unwrap();
2335
2336 let mut buffer = Vec::new();
2337 invoice_request.write(&mut buffer).unwrap();
2338
2339 if let Err(e) = InvoiceRequest::try_from(buffer) {
2340 panic!("error parsing invoice_request: {:?}", e);
2341 }
2342
2343 let invoice_request = OfferBuilder::new(recipient_pubkey())
2344 .build()
2345 .unwrap()
2346 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2347 .unwrap()
2348 .amount_msats(1000)
2349 .unwrap()
2350 .build_and_sign()
2351 .unwrap();
2352
2353 let mut buffer = Vec::new();
2354 invoice_request.write(&mut buffer).unwrap();
2355
2356 if let Err(e) = InvoiceRequest::try_from(buffer) {
2357 panic!("error parsing invoice_request: {:?}", e);
2358 }
2359
2360 let invoice_request = OfferBuilder::new(recipient_pubkey())
2361 .build()
2362 .unwrap()
2363 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2364 .unwrap()
2365 .build_unchecked_and_sign();
2366
2367 let mut buffer = Vec::new();
2368 invoice_request.write(&mut buffer).unwrap();
2369
2370 match InvoiceRequest::try_from(buffer) {
2371 Ok(_) => panic!("expected error"),
2372 Err(e) => assert_eq!(
2373 e,
2374 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::MissingAmount)
2375 ),
2376 }
2377
2378 let invoice_request = OfferBuilder::new(recipient_pubkey())
2379 .amount_msats(1000)
2380 .build()
2381 .unwrap()
2382 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2383 .unwrap()
2384 .amount_msats_unchecked(999)
2385 .build_unchecked_and_sign();
2386
2387 let mut buffer = Vec::new();
2388 invoice_request.write(&mut buffer).unwrap();
2389
2390 match InvoiceRequest::try_from(buffer) {
2391 Ok(_) => panic!("expected error"),
2392 Err(e) => assert_eq!(
2393 e,
2394 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::InsufficientAmount)
2395 ),
2396 }
2397
2398 let invoice_request = OfferBuilder::new(recipient_pubkey())
2399 .description("foo".to_string())
2400 .amount(Amount::Currency {
2401 iso4217_code: CurrencyCode::new(*b"USD").unwrap(),
2402 amount: 1000,
2403 })
2404 .build_unchecked()
2405 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2406 .unwrap()
2407 .build_unchecked_and_sign();
2408
2409 let mut buffer = Vec::new();
2410 invoice_request.write(&mut buffer).unwrap();
2411
2412 match InvoiceRequest::try_from(buffer) {
2413 Ok(_) => panic!("expected error"),
2414 Err(e) => {
2415 assert_eq!(
2416 e,
2417 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::UnsupportedCurrency)
2418 );
2419 },
2420 }
2421
2422 let invoice_request = OfferBuilder::new(recipient_pubkey())
2423 .amount_msats(1000)
2424 .supported_quantity(Quantity::Unbounded)
2425 .build()
2426 .unwrap()
2427 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2428 .unwrap()
2429 .quantity(u64::max_value())
2430 .unwrap()
2431 .build_unchecked_and_sign();
2432
2433 let mut buffer = Vec::new();
2434 invoice_request.write(&mut buffer).unwrap();
2435
2436 match InvoiceRequest::try_from(buffer) {
2437 Ok(_) => panic!("expected error"),
2438 Err(e) => assert_eq!(
2439 e,
2440 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::InvalidAmount)
2441 ),
2442 }
2443 }
2444
2445 #[test]
2446 fn parses_invoice_request_with_quantity() {
2447 let expanded_key = ExpandedKey::new([42; 32]);
2448 let entropy = FixedEntropy {};
2449 let nonce = Nonce::from_entropy_source(&entropy);
2450 let secp_ctx = Secp256k1::new();
2451 let payment_id = PaymentId([1; 32]);
2452
2453 let one = NonZeroU64::new(1).unwrap();
2454 let ten = NonZeroU64::new(10).unwrap();
2455
2456 let invoice_request = OfferBuilder::new(recipient_pubkey())
2457 .amount_msats(1000)
2458 .supported_quantity(Quantity::One)
2459 .build()
2460 .unwrap()
2461 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2462 .unwrap()
2463 .build_and_sign()
2464 .unwrap();
2465
2466 let mut buffer = Vec::new();
2467 invoice_request.write(&mut buffer).unwrap();
2468
2469 if let Err(e) = InvoiceRequest::try_from(buffer) {
2470 panic!("error parsing invoice_request: {:?}", e);
2471 }
2472
2473 let invoice_request = OfferBuilder::new(recipient_pubkey())
2474 .amount_msats(1000)
2475 .supported_quantity(Quantity::One)
2476 .build()
2477 .unwrap()
2478 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2479 .unwrap()
2480 .amount_msats(2_000)
2481 .unwrap()
2482 .quantity_unchecked(2)
2483 .build_unchecked_and_sign();
2484
2485 let mut buffer = Vec::new();
2486 invoice_request.write(&mut buffer).unwrap();
2487
2488 match InvoiceRequest::try_from(buffer) {
2489 Ok(_) => panic!("expected error"),
2490 Err(e) => {
2491 assert_eq!(
2492 e,
2493 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::UnexpectedQuantity)
2494 );
2495 },
2496 }
2497
2498 let invoice_request = OfferBuilder::new(recipient_pubkey())
2499 .amount_msats(1000)
2500 .supported_quantity(Quantity::Bounded(ten))
2501 .build()
2502 .unwrap()
2503 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2504 .unwrap()
2505 .amount_msats(10_000)
2506 .unwrap()
2507 .quantity(10)
2508 .unwrap()
2509 .build_and_sign()
2510 .unwrap();
2511
2512 let mut buffer = Vec::new();
2513 invoice_request.write(&mut buffer).unwrap();
2514
2515 if let Err(e) = InvoiceRequest::try_from(buffer) {
2516 panic!("error parsing invoice_request: {:?}", e);
2517 }
2518
2519 let invoice_request = OfferBuilder::new(recipient_pubkey())
2520 .amount_msats(1000)
2521 .supported_quantity(Quantity::Bounded(ten))
2522 .build()
2523 .unwrap()
2524 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2525 .unwrap()
2526 .amount_msats(11_000)
2527 .unwrap()
2528 .quantity_unchecked(11)
2529 .build_unchecked_and_sign();
2530
2531 let mut buffer = Vec::new();
2532 invoice_request.write(&mut buffer).unwrap();
2533
2534 match InvoiceRequest::try_from(buffer) {
2535 Ok(_) => panic!("expected error"),
2536 Err(e) => assert_eq!(
2537 e,
2538 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::InvalidQuantity)
2539 ),
2540 }
2541
2542 let invoice_request = OfferBuilder::new(recipient_pubkey())
2543 .amount_msats(1000)
2544 .supported_quantity(Quantity::Unbounded)
2545 .build()
2546 .unwrap()
2547 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2548 .unwrap()
2549 .amount_msats(2_000)
2550 .unwrap()
2551 .quantity(2)
2552 .unwrap()
2553 .build_and_sign()
2554 .unwrap();
2555
2556 let mut buffer = Vec::new();
2557 invoice_request.write(&mut buffer).unwrap();
2558
2559 if let Err(e) = InvoiceRequest::try_from(buffer) {
2560 panic!("error parsing invoice_request: {:?}", e);
2561 }
2562
2563 let invoice_request = OfferBuilder::new(recipient_pubkey())
2564 .amount_msats(1000)
2565 .supported_quantity(Quantity::Unbounded)
2566 .build()
2567 .unwrap()
2568 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2569 .unwrap()
2570 .build_unchecked_and_sign();
2571
2572 let mut buffer = Vec::new();
2573 invoice_request.write(&mut buffer).unwrap();
2574
2575 match InvoiceRequest::try_from(buffer) {
2576 Ok(_) => panic!("expected error"),
2577 Err(e) => assert_eq!(
2578 e,
2579 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::MissingQuantity)
2580 ),
2581 }
2582
2583 let invoice_request = OfferBuilder::new(recipient_pubkey())
2584 .amount_msats(1000)
2585 .supported_quantity(Quantity::Bounded(one))
2586 .build()
2587 .unwrap()
2588 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2589 .unwrap()
2590 .build_unchecked_and_sign();
2591
2592 let mut buffer = Vec::new();
2593 invoice_request.write(&mut buffer).unwrap();
2594
2595 match InvoiceRequest::try_from(buffer) {
2596 Ok(_) => panic!("expected error"),
2597 Err(e) => assert_eq!(
2598 e,
2599 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::MissingQuantity)
2600 ),
2601 }
2602 }
2603
2604 #[test]
2605 fn fails_parsing_invoice_request_without_metadata() {
2606 let expanded_key = ExpandedKey::new([42; 32]);
2607 let entropy = FixedEntropy {};
2608 let nonce = Nonce::from_entropy_source(&entropy);
2609 let secp_ctx = Secp256k1::new();
2610 let payment_id = PaymentId([1; 32]);
2611
2612 let unsigned_invoice_request = OfferBuilder::new(recipient_pubkey())
2613 .amount_msats(1000)
2614 .build()
2615 .unwrap()
2616 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2617 .unwrap()
2618 .build_unchecked();
2619 let mut tlv_stream = unsigned_invoice_request.contents.as_tlv_stream();
2620 tlv_stream.0.metadata = None;
2621
2622 let mut buffer = Vec::new();
2623 tlv_stream.write(&mut buffer).unwrap();
2624
2625 match InvoiceRequest::try_from(buffer) {
2626 Ok(_) => panic!("expected error"),
2627 Err(e) => {
2628 assert_eq!(
2629 e,
2630 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::MissingPayerMetadata)
2631 );
2632 },
2633 }
2634 }
2635
2636 #[test]
2637 fn fails_parsing_invoice_request_without_payer_signing_pubkey() {
2638 let expanded_key = ExpandedKey::new([42; 32]);
2639 let entropy = FixedEntropy {};
2640 let nonce = Nonce::from_entropy_source(&entropy);
2641 let secp_ctx = Secp256k1::new();
2642 let payment_id = PaymentId([1; 32]);
2643
2644 let unsigned_invoice_request = OfferBuilder::new(recipient_pubkey())
2645 .amount_msats(1000)
2646 .build()
2647 .unwrap()
2648 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2649 .unwrap()
2650 .build_unchecked();
2651 let mut tlv_stream = unsigned_invoice_request.contents.as_tlv_stream();
2652 tlv_stream.2.payer_id = None;
2653
2654 let mut buffer = Vec::new();
2655 tlv_stream.write(&mut buffer).unwrap();
2656
2657 match InvoiceRequest::try_from(buffer) {
2658 Ok(_) => panic!("expected error"),
2659 Err(e) => assert_eq!(
2660 e,
2661 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::MissingPayerSigningPubkey)
2662 ),
2663 }
2664 }
2665
2666 #[test]
2667 fn fails_parsing_invoice_request_without_issuer_id() {
2668 let expanded_key = ExpandedKey::new([42; 32]);
2669 let entropy = FixedEntropy {};
2670 let nonce = Nonce::from_entropy_source(&entropy);
2671 let secp_ctx = Secp256k1::new();
2672 let payment_id = PaymentId([1; 32]);
2673
2674 let unsigned_invoice_request = OfferBuilder::new(recipient_pubkey())
2675 .amount_msats(1000)
2676 .build()
2677 .unwrap()
2678 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2679 .unwrap()
2680 .build_unchecked();
2681 let mut tlv_stream = unsigned_invoice_request.contents.as_tlv_stream();
2682 tlv_stream.1.issuer_id = None;
2683
2684 let mut buffer = Vec::new();
2685 tlv_stream.write(&mut buffer).unwrap();
2686
2687 match InvoiceRequest::try_from(buffer) {
2688 Ok(_) => panic!("expected error"),
2689 Err(e) => {
2690 assert_eq!(
2691 e,
2692 Bolt12ParseError::InvalidSemantics(
2693 Bolt12SemanticError::MissingIssuerSigningPubkey
2694 )
2695 );
2696 },
2697 }
2698 }
2699
2700 #[test]
2701 fn fails_parsing_invoice_request_without_signature() {
2702 let expanded_key = ExpandedKey::new([42; 32]);
2703 let entropy = FixedEntropy {};
2704 let nonce = Nonce::from_entropy_source(&entropy);
2705 let secp_ctx = Secp256k1::new();
2706 let payment_id = PaymentId([1; 32]);
2707
2708 let mut buffer = Vec::new();
2709 OfferBuilder::new(recipient_pubkey())
2710 .amount_msats(1000)
2711 .build()
2712 .unwrap()
2713 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2714 .unwrap()
2715 .build_unchecked()
2716 .contents
2717 .write(&mut buffer)
2718 .unwrap();
2719
2720 match InvoiceRequest::try_from(buffer) {
2721 Ok(_) => panic!("expected error"),
2722 Err(e) => assert_eq!(
2723 e,
2724 Bolt12ParseError::InvalidSemantics(Bolt12SemanticError::MissingSignature)
2725 ),
2726 }
2727 }
2728
2729 #[test]
2730 fn fails_parsing_invoice_request_with_invalid_signature() {
2731 let expanded_key = ExpandedKey::new([42; 32]);
2732 let entropy = FixedEntropy {};
2733 let nonce = Nonce::from_entropy_source(&entropy);
2734 let secp_ctx = Secp256k1::new();
2735 let payment_id = PaymentId([1; 32]);
2736
2737 let mut invoice_request = OfferBuilder::new(recipient_pubkey())
2738 .amount_msats(1000)
2739 .build()
2740 .unwrap()
2741 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2742 .unwrap()
2743 .build_and_sign()
2744 .unwrap();
2745 let last_signature_byte = invoice_request.bytes.last_mut().unwrap();
2746 *last_signature_byte = last_signature_byte.wrapping_add(1);
2747
2748 let mut buffer = Vec::new();
2749 invoice_request.write(&mut buffer).unwrap();
2750
2751 match InvoiceRequest::try_from(buffer) {
2752 Ok(_) => panic!("expected error"),
2753 Err(e) => {
2754 assert_eq!(
2755 e,
2756 Bolt12ParseError::InvalidSignature(secp256k1::Error::IncorrectSignature)
2757 );
2758 },
2759 }
2760 }
2761
2762 #[test]
2763 fn parses_invoice_request_with_unknown_tlv_records() {
2764 let expanded_key = ExpandedKey::new([42; 32]);
2765 let entropy = FixedEntropy {};
2766 let nonce = Nonce::from_entropy_source(&entropy);
2767 let payment_id = PaymentId([1; 32]);
2768
2769 const UNKNOWN_ODD_TYPE: u64 = INVOICE_REQUEST_TYPES.end - 1;
2770 assert!(UNKNOWN_ODD_TYPE % 2 == 1);
2771
2772 let secp_ctx = Secp256k1::new();
2773 let keys = Keypair::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[42; 32]).unwrap());
2774 let (mut unsigned_invoice_request, payer_keys, _) = OfferBuilder::new(keys.public_key())
2775 .amount_msats(1000)
2776 .build()
2777 .unwrap()
2778 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2779 .unwrap()
2780 .build_without_checks();
2781
2782 let mut unknown_bytes = Vec::new();
2783 BigSize(UNKNOWN_ODD_TYPE).write(&mut unknown_bytes).unwrap();
2784 BigSize(32).write(&mut unknown_bytes).unwrap();
2785 [42u8; 32].write(&mut unknown_bytes).unwrap();
2786
2787 unsigned_invoice_request.bytes.extend_from_slice(&unknown_bytes);
2788 unsigned_invoice_request.tagged_hash =
2789 TaggedHash::from_valid_tlv_stream_bytes(SIGNATURE_TAG, &unsigned_invoice_request.bytes);
2790
2791 let keys = payer_keys.unwrap();
2792 let invoice_request = unsigned_invoice_request
2793 .sign(|message: &UnsignedInvoiceRequest| {
2794 Ok(secp_ctx.sign_schnorr_no_aux_rand(message.as_ref().as_digest(), &keys))
2795 })
2796 .unwrap();
2797
2798 let mut encoded_invoice_request = Vec::new();
2799 invoice_request.write(&mut encoded_invoice_request).unwrap();
2800
2801 match InvoiceRequest::try_from(encoded_invoice_request.clone()) {
2802 Ok(invoice_request) => assert_eq!(invoice_request.bytes, encoded_invoice_request),
2803 Err(e) => panic!("error parsing invoice_request: {:?}", e),
2804 }
2805
2806 const UNKNOWN_EVEN_TYPE: u64 = INVOICE_REQUEST_TYPES.end - 2;
2807 assert!(UNKNOWN_EVEN_TYPE % 2 == 0);
2808
2809 let (mut unsigned_invoice_request, payer_keys, _) = OfferBuilder::new(keys.public_key())
2810 .amount_msats(1000)
2811 .build()
2812 .unwrap()
2813 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2814 .unwrap()
2815 .build_without_checks();
2816
2817 let mut unknown_bytes = Vec::new();
2818 BigSize(UNKNOWN_EVEN_TYPE).write(&mut unknown_bytes).unwrap();
2819 BigSize(32).write(&mut unknown_bytes).unwrap();
2820 [42u8; 32].write(&mut unknown_bytes).unwrap();
2821
2822 unsigned_invoice_request.bytes.extend_from_slice(&unknown_bytes);
2823 unsigned_invoice_request.tagged_hash =
2824 TaggedHash::from_valid_tlv_stream_bytes(SIGNATURE_TAG, &unsigned_invoice_request.bytes);
2825
2826 let keys = payer_keys.unwrap();
2827 let invoice_request = unsigned_invoice_request
2828 .sign(|message: &UnsignedInvoiceRequest| {
2829 Ok(secp_ctx.sign_schnorr_no_aux_rand(message.as_ref().as_digest(), &keys))
2830 })
2831 .unwrap();
2832
2833 let mut encoded_invoice_request = Vec::new();
2834 invoice_request.write(&mut encoded_invoice_request).unwrap();
2835
2836 match InvoiceRequest::try_from(encoded_invoice_request) {
2837 Ok(_) => panic!("expected error"),
2838 Err(e) => assert_eq!(e, Bolt12ParseError::Decode(DecodeError::UnknownRequiredFeature)),
2839 }
2840 }
2841
2842 #[test]
2843 fn parses_invoice_request_with_experimental_tlv_records() {
2844 let expanded_key = ExpandedKey::new([42; 32]);
2845 let entropy = FixedEntropy {};
2846 let nonce = Nonce::from_entropy_source(&entropy);
2847 let payment_id = PaymentId([1; 32]);
2848
2849 const UNKNOWN_ODD_TYPE: u64 = EXPERIMENTAL_INVOICE_REQUEST_TYPES.start + 1;
2850 assert!(UNKNOWN_ODD_TYPE % 2 == 1);
2851
2852 let secp_ctx = Secp256k1::new();
2853 let keys = Keypair::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[42; 32]).unwrap());
2854 let (mut unsigned_invoice_request, payer_keys, _) = OfferBuilder::new(keys.public_key())
2855 .amount_msats(1000)
2856 .build()
2857 .unwrap()
2858 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2859 .unwrap()
2860 .build_without_checks();
2861
2862 let mut unknown_bytes = Vec::new();
2863 BigSize(UNKNOWN_ODD_TYPE).write(&mut unknown_bytes).unwrap();
2864 BigSize(32).write(&mut unknown_bytes).unwrap();
2865 [42u8; 32].write(&mut unknown_bytes).unwrap();
2866
2867 unsigned_invoice_request.experimental_bytes.extend_from_slice(&unknown_bytes);
2868
2869 let tlv_stream = TlvStream::new(&unsigned_invoice_request.bytes)
2870 .chain(TlvStream::new(&unsigned_invoice_request.experimental_bytes));
2871 unsigned_invoice_request.tagged_hash =
2872 TaggedHash::from_tlv_stream(SIGNATURE_TAG, tlv_stream);
2873
2874 let keys = payer_keys.unwrap();
2875 let invoice_request = unsigned_invoice_request
2876 .sign(|message: &UnsignedInvoiceRequest| {
2877 Ok(secp_ctx.sign_schnorr_no_aux_rand(message.as_ref().as_digest(), &keys))
2878 })
2879 .unwrap();
2880
2881 let mut encoded_invoice_request = Vec::new();
2882 invoice_request.write(&mut encoded_invoice_request).unwrap();
2883
2884 match InvoiceRequest::try_from(encoded_invoice_request.clone()) {
2885 Ok(invoice_request) => assert_eq!(invoice_request.bytes, encoded_invoice_request),
2886 Err(e) => panic!("error parsing invoice_request: {:?}", e),
2887 }
2888
2889 const UNKNOWN_EVEN_TYPE: u64 = EXPERIMENTAL_INVOICE_REQUEST_TYPES.start;
2890 assert!(UNKNOWN_EVEN_TYPE % 2 == 0);
2891
2892 let (mut unsigned_invoice_request, payer_keys, _) = OfferBuilder::new(keys.public_key())
2893 .amount_msats(1000)
2894 .build()
2895 .unwrap()
2896 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2897 .unwrap()
2898 .build_without_checks();
2899
2900 let mut unknown_bytes = Vec::new();
2901 BigSize(UNKNOWN_EVEN_TYPE).write(&mut unknown_bytes).unwrap();
2902 BigSize(32).write(&mut unknown_bytes).unwrap();
2903 [42u8; 32].write(&mut unknown_bytes).unwrap();
2904
2905 unsigned_invoice_request.experimental_bytes.extend_from_slice(&unknown_bytes);
2906
2907 let tlv_stream = TlvStream::new(&unsigned_invoice_request.bytes)
2908 .chain(TlvStream::new(&unsigned_invoice_request.experimental_bytes));
2909 unsigned_invoice_request.tagged_hash =
2910 TaggedHash::from_tlv_stream(SIGNATURE_TAG, tlv_stream);
2911
2912 let keys = payer_keys.unwrap();
2913 let invoice_request = unsigned_invoice_request
2914 .sign(|message: &UnsignedInvoiceRequest| {
2915 Ok(secp_ctx.sign_schnorr_no_aux_rand(message.as_ref().as_digest(), &keys))
2916 })
2917 .unwrap();
2918
2919 let mut encoded_invoice_request = Vec::new();
2920 invoice_request.write(&mut encoded_invoice_request).unwrap();
2921
2922 match InvoiceRequest::try_from(encoded_invoice_request) {
2923 Ok(_) => panic!("expected error"),
2924 Err(e) => assert_eq!(e, Bolt12ParseError::Decode(DecodeError::UnknownRequiredFeature)),
2925 }
2926
2927 let invoice_request = OfferBuilder::new(keys.public_key())
2928 .amount_msats(1000)
2929 .build()
2930 .unwrap()
2931 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2932 .unwrap()
2933 .build_and_sign()
2934 .unwrap();
2935
2936 let mut encoded_invoice_request = Vec::new();
2937 invoice_request.write(&mut encoded_invoice_request).unwrap();
2938
2939 BigSize(UNKNOWN_ODD_TYPE).write(&mut encoded_invoice_request).unwrap();
2940 BigSize(32).write(&mut encoded_invoice_request).unwrap();
2941 [42u8; 32].write(&mut encoded_invoice_request).unwrap();
2942
2943 match InvoiceRequest::try_from(encoded_invoice_request) {
2944 Ok(_) => panic!("expected error"),
2945 Err(e) => assert_eq!(
2946 e,
2947 Bolt12ParseError::InvalidSignature(secp256k1::Error::IncorrectSignature)
2948 ),
2949 }
2950 }
2951
2952 #[test]
2953 fn fails_parsing_invoice_request_with_out_of_range_tlv_records() {
2954 let expanded_key = ExpandedKey::new([42; 32]);
2955 let entropy = FixedEntropy {};
2956 let nonce = Nonce::from_entropy_source(&entropy);
2957 let secp_ctx = Secp256k1::new();
2958 let payment_id = PaymentId([1; 32]);
2959
2960 let invoice_request = OfferBuilder::new(recipient_pubkey())
2961 .amount_msats(1000)
2962 .build()
2963 .unwrap()
2964 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
2965 .unwrap()
2966 .build_and_sign()
2967 .unwrap();
2968
2969 let mut encoded_invoice_request = Vec::new();
2970 invoice_request.write(&mut encoded_invoice_request).unwrap();
2971 BigSize(1002).write(&mut encoded_invoice_request).unwrap();
2972 BigSize(32).write(&mut encoded_invoice_request).unwrap();
2973 [42u8; 32].write(&mut encoded_invoice_request).unwrap();
2974
2975 match InvoiceRequest::try_from(encoded_invoice_request) {
2976 Ok(_) => panic!("expected error"),
2977 Err(e) => assert_eq!(e, Bolt12ParseError::Decode(DecodeError::InvalidValue)),
2978 }
2979
2980 let mut encoded_invoice_request = Vec::new();
2981 invoice_request.write(&mut encoded_invoice_request).unwrap();
2982 BigSize(EXPERIMENTAL_INVOICE_REQUEST_TYPES.end)
2983 .write(&mut encoded_invoice_request)
2984 .unwrap();
2985 BigSize(32).write(&mut encoded_invoice_request).unwrap();
2986 [42u8; 32].write(&mut encoded_invoice_request).unwrap();
2987
2988 match InvoiceRequest::try_from(encoded_invoice_request) {
2989 Ok(_) => panic!("expected error"),
2990 Err(e) => assert_eq!(e, Bolt12ParseError::Decode(DecodeError::InvalidValue)),
2991 }
2992 }
2993
2994 #[test]
2995 fn copies_verified_invoice_request_fields() {
2996 let node_id = recipient_pubkey();
2997 let expanded_key = ExpandedKey::new([42; 32]);
2998 let entropy = FixedEntropy {};
2999 let nonce = Nonce::from_entropy_source(&entropy);
3000 let secp_ctx = Secp256k1::new();
3001 let payment_id = PaymentId([1; 32]);
3002
3003 #[cfg(c_bindings)]
3004 use crate::offers::offer::OfferWithDerivedMetadataBuilder as OfferBuilder;
3005 let offer = OfferBuilder::deriving_signing_pubkey(node_id, &expanded_key, nonce, &secp_ctx)
3006 .chain(Network::Testnet)
3007 .amount_msats(1000)
3008 .supported_quantity(Quantity::Unbounded)
3009 .build()
3010 .unwrap();
3011 assert_eq!(offer.issuer_signing_pubkey(), Some(node_id));
3012
3013 let payer_note = "❤️".repeat(86);
3016 assert_eq!(payer_note.len(), PAYER_NOTE_LIMIT + 4);
3017 let expected_payer_note = "❤️".repeat(85);
3018
3019 let invoice_request = offer
3020 .request_invoice(&expanded_key, nonce, &secp_ctx, payment_id)
3021 .unwrap()
3022 .chain(Network::Testnet)
3023 .unwrap()
3024 .quantity(1)
3025 .unwrap()
3026 .payer_note(payer_note)
3027 .build_and_sign()
3028 .unwrap();
3029 match invoice_request.verify_using_metadata(&expanded_key, &secp_ctx) {
3030 Ok(invoice_request) => {
3031 let fields = invoice_request.fields();
3032 assert_eq!(invoice_request.offer_id, offer.id());
3033 assert_eq!(
3034 fields,
3035 InvoiceRequestFields {
3036 payer_signing_pubkey: invoice_request.payer_signing_pubkey(),
3037 quantity: Some(1),
3038 payer_note_truncated: Some(UntrustedString(expected_payer_note)),
3039 human_readable_name: None,
3040 }
3041 );
3042
3043 let mut buffer = Vec::new();
3044 fields.write(&mut buffer).unwrap();
3045
3046 let deserialized_fields: InvoiceRequestFields =
3047 Readable::read(&mut buffer.as_slice()).unwrap();
3048 assert_eq!(deserialized_fields, fields);
3049 },
3050 Err(_) => panic!("unexpected error"),
3051 }
3052 }
3053
3054 #[test]
3055 fn test_string_truncate_safe() {
3056 let s = String::from("❤️");
3060 assert_eq!(s.len(), 6);
3061 assert_eq!(s, string_truncate_safe(s.clone(), 7));
3062 assert_eq!(s, string_truncate_safe(s.clone(), 6));
3063 assert_eq!("❤", string_truncate_safe(s.clone(), 5));
3064 assert_eq!("❤", string_truncate_safe(s.clone(), 4));
3065 assert_eq!("❤", string_truncate_safe(s.clone(), 3));
3066 assert_eq!("", string_truncate_safe(s.clone(), 2));
3067 assert_eq!("", string_truncate_safe(s.clone(), 1));
3068 assert_eq!("", string_truncate_safe(s.clone(), 0));
3069
3070 let s = String::from("my ASCII string!");
3072 for new_len in 0..(s.len() + 5) {
3073 if new_len >= s.len() {
3074 assert_eq!(s, string_truncate_safe(s.clone(), new_len));
3075 } else {
3076 assert_eq!(s[..new_len], string_truncate_safe(s.clone(), new_len));
3077 }
3078 }
3079 }
3080}