@@ -10,6 +10,7 @@ import (
1010 "github.com/btcsuite/btcd/btcutil"
1111 "github.com/lightningnetwork/lnd/chainreg"
1212 "github.com/lightningnetwork/lnd/lnrpc"
13+ "github.com/lightningnetwork/lnd/lnrpc/invoicesrpc"
1314 "github.com/lightningnetwork/lnd/lnrpc/routerrpc"
1415 "github.com/lightningnetwork/lnd/lntest"
1516 "github.com/lightningnetwork/lnd/lntest/node"
@@ -374,8 +375,13 @@ func testForwardInterceptorModifiedHtlc(ht *lntest.HarnessTest) {
374375 // Connect an interceptor to Bob's node.
375376 bobInterceptor , cancelBobInterceptor := bob .RPC .HtlcInterceptor ()
376377
378+ // We're going to modify the payment amount and want Carol to accept the
379+ // payment, so we set up an invoice acceptor on Dave.
380+ carolAcceptor , carolCancel := carol .RPC .InvoiceHtlcModifier ()
381+ defer carolCancel ()
382+
377383 // Prepare the test cases.
378- invoiceValueAmtMsat := int64 (1000 )
384+ invoiceValueAmtMsat := int64 (20_000_000 )
379385 req := & lnrpc.Invoice {ValueMsat : invoiceValueAmtMsat }
380386 addResponse := carol .RPC .AddInvoice (req )
381387 invoice := carol .RPC .LookupInvoice (addResponse .RHash )
@@ -408,10 +414,10 @@ func testForwardInterceptorModifiedHtlc(ht *lntest.HarnessTest) {
408414 crValue := []byte ("custom-records-test-value" )
409415 customRecords [crKey ] = crValue
410416
411- // TODO(guggero): Actually modify the amount once we have the invoice
412- // interceptor and can accept a lower amount.
413- newOutAmountMsat := packet . OutgoingAmountMsat
414-
417+ // Modify the amount of the HTLC, so we send out less than the original
418+ // amount.
419+ const modifyAmount = 5_000_000
420+ newOutAmountMsat := packet . OutgoingAmountMsat - modifyAmount
415421 err := bobInterceptor .Send (& routerrpc.ForwardHtlcInterceptResponse {
416422 IncomingCircuitKey : packet .IncomingCircuitKey ,
417423 OutAmountMsat : newOutAmountMsat ,
@@ -420,6 +426,17 @@ func testForwardInterceptorModifiedHtlc(ht *lntest.HarnessTest) {
420426 })
421427 require .NoError (ht , err , "failed to send request" )
422428
429+ invoicePacket := ht .ReceiveInvoiceHtlcModification (carolAcceptor )
430+ require .EqualValues (
431+ ht , newOutAmountMsat , invoicePacket .ExitHtlcAmt ,
432+ )
433+ amtPaid := newOutAmountMsat + modifyAmount
434+ err = carolAcceptor .Send (& invoicesrpc.HtlcModifyResponse {
435+ CircuitKey : invoicePacket .ExitHtlcCircuitKey ,
436+ AmtPaid : & amtPaid ,
437+ })
438+ require .NoError (ht , err , "carol acceptor response" )
439+
423440 // Cancel the context, which will disconnect Bob's interceptor.
424441 cancelBobInterceptor ()
425442
@@ -473,17 +490,23 @@ func testForwardInterceptorWireRecords(ht *lntest.HarnessTest) {
473490 carolInterceptor , cancelCarolInterceptor := carol .RPC .HtlcInterceptor ()
474491 defer cancelCarolInterceptor ()
475492
476- req := & lnrpc.Invoice {ValueMsat : 1000 }
493+ // We're going to modify the payment amount and want Dave to accept the
494+ // payment, so we set up an invoice acceptor on Dave.
495+ daveAcceptor , daveCancel := dave .RPC .InvoiceHtlcModifier ()
496+ defer daveCancel ()
497+
498+ req := & lnrpc.Invoice {ValueMsat : 20_000_000 }
477499 addResponse := dave .RPC .AddInvoice (req )
478500 invoice := dave .RPC .LookupInvoice (addResponse .RHash )
479501
502+ customRecords := map [uint64 ][]byte {
503+ 65537 : []byte ("test" ),
504+ }
480505 sendReq := & routerrpc.SendPaymentRequest {
481- PaymentRequest : invoice .PaymentRequest ,
482- TimeoutSeconds : int32 (wait .PaymentTimeout .Seconds ()),
483- FeeLimitMsat : noFeeLimitMsat ,
484- FirstHopCustomRecords : map [uint64 ][]byte {
485- 65537 : []byte ("test" ),
486- },
506+ PaymentRequest : invoice .PaymentRequest ,
507+ TimeoutSeconds : int32 (wait .PaymentTimeout .Seconds ()),
508+ FeeLimitMsat : noFeeLimitMsat ,
509+ FirstHopCustomRecords : customRecords ,
487510 }
488511
489512 _ = alice .RPC .SendPayment (sendReq )
@@ -499,14 +522,10 @@ func testForwardInterceptorWireRecords(ht *lntest.HarnessTest) {
499522 require .True (ht , ok , "expected custom record" )
500523 require .Equal (ht , []byte ("test" ), val )
501524
502- // TODO(guggero): Actually modify the amount once we have the invoice
503- // interceptor and can accept a lower amount.
504- newOutAmountMsat := packet .OutgoingAmountMsat
505-
525+ // Just resume the payment on Bob.
506526 err := bobInterceptor .Send (& routerrpc.ForwardHtlcInterceptResponse {
507527 IncomingCircuitKey : packet .IncomingCircuitKey ,
508- OutAmountMsat : newOutAmountMsat ,
509- Action : actionResumeModify ,
528+ Action : actionResume ,
510529 })
511530 require .NoError (ht , err , "failed to send request" )
512531
@@ -515,13 +534,32 @@ func testForwardInterceptorWireRecords(ht *lntest.HarnessTest) {
515534 packet = ht .ReceiveHtlcInterceptor (carolInterceptor )
516535 require .Len (ht , packet .InWireCustomRecords , 0 )
517536
518- // Just resume the payment on Carol.
537+ // We're going to tell Carol to forward 5k sats less to Dave. We need to
538+ // set custom records on the HTLC as well, to make sure the HTLC isn't
539+ // rejected outright and actually gets to the invoice acceptor.
540+ const modifyAmount = 5_000_000
541+ newOutAmountMsat := packet .OutgoingAmountMsat - modifyAmount
519542 err = carolInterceptor .Send (& routerrpc.ForwardHtlcInterceptResponse {
520- IncomingCircuitKey : packet .IncomingCircuitKey ,
521- Action : actionResume ,
543+ IncomingCircuitKey : packet .IncomingCircuitKey ,
544+ OutAmountMsat : newOutAmountMsat ,
545+ OutWireCustomRecords : customRecords ,
546+ Action : actionResumeModify ,
522547 })
523548 require .NoError (ht , err , "carol interceptor response" )
524549
550+ // The payment should get to Dave, and we should be able to intercept
551+ // and modify it, telling Dave to accept it.
552+ invoicePacket := ht .ReceiveInvoiceHtlcModification (daveAcceptor )
553+ require .EqualValues (
554+ ht , newOutAmountMsat , invoicePacket .ExitHtlcAmt ,
555+ )
556+ amtPaid := newOutAmountMsat + modifyAmount
557+ err = daveAcceptor .Send (& invoicesrpc.HtlcModifyResponse {
558+ CircuitKey : invoicePacket .ExitHtlcCircuitKey ,
559+ AmtPaid : & amtPaid ,
560+ })
561+ require .NoError (ht , err , "dave acceptor response" )
562+
525563 // Assert that the payment was successful.
526564 var preimage lntypes.Preimage
527565 copy (preimage [:], invoice .RPreimage )
0 commit comments