Skip to content

Commit c736333

Browse files
committed
itest: add custom channels multi rfq receive itest
1 parent 58adc54 commit c736333

File tree

2 files changed

+165
-5
lines changed

2 files changed

+165
-5
lines changed

itest/litd_custom_channels_test.go

Lines changed: 160 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ var (
4848
AssetType: taprpc.AssetType_NORMAL,
4949
Name: "itest-asset-cents",
5050
AssetMeta: dummyMetaData,
51-
Amount: 1_000_000,
51+
Amount: 10_000_000,
5252
}
5353

5454
shortTimeout = time.Second * 5
@@ -2720,14 +2720,15 @@ func testCustomChannelsLiquidtyEdgeCasesCore(ctx context.Context,
27202720
t.Logf("Universes synced between all nodes, distributing assets...")
27212721

27222722
const (
2723-
daveFundingAmount = uint64(400_000)
2724-
erinFundingAmount = uint64(200_000)
2723+
daveFundingAmount = uint64(400_000)
2724+
erinFundingAmount = uint64(200_000)
2725+
charlieFundingAmount = uint64(400_000)
27252726
)
2726-
charlieFundingAmount := cents.Amount - uint64(2*400_000)
2727+
// charlieFundingAmount := cents.Amount - uint64(2*400_000)
27272728

27282729
_, _, _ = createTestAssetNetwork(
27292730
t, net, charlieTap, daveTap, erinTap, fabiaTap, yaraTap,
2730-
universeTap, cents, 400_000, charlieFundingAmount,
2731+
universeTap, cents, 500_000, charlieFundingAmount,
27312732
daveFundingAmount, erinFundingAmount, 0,
27322733
)
27332734

@@ -3126,6 +3127,160 @@ func testCustomChannelsLiquidityEdgeCasesGroup(ctx context.Context,
31263127
testCustomChannelsLiquidtyEdgeCasesCore(ctx, net, t, true)
31273128
}
31283129

3130+
// testCustomChannelsMultiRFQReceive tests that a node creating an invoice with
3131+
// multiple RFQ quotes can actually guide the payer into using multiple private
3132+
// taproot asset channels to pay the invoice.
3133+
func testCustomChannelsMultiRFQReceive(ctx context.Context, net *NetworkHarness,
3134+
t *harnessTest) {
3135+
3136+
lndArgs := slices.Clone(lndArgsTemplate)
3137+
litdArgs := slices.Clone(litdArgsTemplate)
3138+
3139+
// Explicitly set the proof courier as Zane (now has no other role
3140+
// other than proof shuffling), otherwise a hashmail courier will be
3141+
// used. For the funding transaction, we're just posting it and don't
3142+
// expect a true receiver.
3143+
zane, err := net.NewNode(
3144+
t.t, "Zane", lndArgs, false, true, litdArgs...,
3145+
)
3146+
require.NoError(t.t, err)
3147+
3148+
litdArgs = append(litdArgs, fmt.Sprintf(
3149+
"--taproot-assets.proofcourieraddr=%s://%s",
3150+
proof.UniverseRpcCourierType, zane.Cfg.LitAddr(),
3151+
))
3152+
3153+
charlie, err := net.NewNode(
3154+
t.t, "Charlie", lndArgs, false, true, litdArgs...,
3155+
)
3156+
require.NoError(t.t, err)
3157+
3158+
dave, err := net.NewNode(t.t, "Dave", lndArgs, false, true, litdArgs...)
3159+
require.NoError(t.t, err)
3160+
erin, err := net.NewNode(t.t, "Erin", lndArgs, false, true, litdArgs...)
3161+
require.NoError(t.t, err)
3162+
fabia, err := net.NewNode(
3163+
t.t, "Fabia", lndArgs, false, true, litdArgs...,
3164+
)
3165+
require.NoError(t.t, err)
3166+
yara, err := net.NewNode(
3167+
t.t, "Yara", lndArgs, false, true, litdArgs...,
3168+
)
3169+
require.NoError(t.t, err)
3170+
3171+
nodes := []*HarnessNode{charlie, dave, erin, fabia, yara}
3172+
connectAllNodes(t.t, net, nodes)
3173+
fundAllNodes(t.t, net, nodes)
3174+
3175+
// The topology we are going for looks like the following:
3176+
//
3177+
// /---[sats]--> Erin --[assets]--\
3178+
// / \
3179+
// / \
3180+
// Charlie -----[sats]--> Dave --[assets]---->Fabia
3181+
// \ /
3182+
// \ /
3183+
// \---[sats]--> Yara --[assets]--/
3184+
//
3185+
3186+
// Let's open the normal sats channels between Charlie and the routing
3187+
// peers.
3188+
_ = openChannelAndAssert(
3189+
t, net, charlie, erin, lntest.OpenChannelParams{
3190+
Amt: 10_000_000,
3191+
SatPerVByte: 5,
3192+
},
3193+
)
3194+
3195+
_ = openChannelAndAssert(
3196+
t, net, charlie, dave, lntest.OpenChannelParams{
3197+
Amt: 10_000_000,
3198+
SatPerVByte: 5,
3199+
},
3200+
)
3201+
3202+
_ = openChannelAndAssert(
3203+
t, net, charlie, yara, lntest.OpenChannelParams{
3204+
Amt: 10_000_000,
3205+
SatPerVByte: 5,
3206+
},
3207+
)
3208+
3209+
// Let's create the tap clients.
3210+
universeTap := newTapClient(t.t, zane)
3211+
charlieTap := newTapClient(t.t, charlie)
3212+
daveTap := newTapClient(t.t, dave)
3213+
erinTap := newTapClient(t.t, erin)
3214+
fabiaTap := newTapClient(t.t, fabia)
3215+
yaraTap := newTapClient(t.t, yara)
3216+
3217+
assetReq := itest.CopyRequest(&mintrpc.MintAssetRequest{
3218+
Asset: itestAsset,
3219+
})
3220+
3221+
assetReq.Asset.NewGroupedAsset = true
3222+
3223+
// Mint an asset on Charlie and sync all nodes to Charlie as the
3224+
// universe.
3225+
mintedAssets := itest.MintAssetsConfirmBatch(
3226+
t.t, t.lndHarness.Miner.Client, charlieTap,
3227+
[]*mintrpc.MintAssetRequest{assetReq},
3228+
)
3229+
cents := mintedAssets[0]
3230+
assetID := cents.AssetGenesis.AssetId
3231+
groupID := cents.GetAssetGroup().GetTweakedGroupKey()
3232+
3233+
syncUniverses(t.t, charlieTap, dave, erin, fabia, yara)
3234+
3235+
createTestMultiRFQAssetNetwork(
3236+
t, net, charlieTap, daveTap, erinTap, fabiaTap, yaraTap,
3237+
universeTap, cents, 10_000, 10_000, 10_000,
3238+
)
3239+
3240+
logBalance(t.t, nodes, assetID, "before multi-rfq receive")
3241+
3242+
hodlInv := createAssetHodlInvoice(t.t, nil, fabia, 20_000, assetID)
3243+
3244+
payInvoiceWithSatoshi(
3245+
t.t, charlie, &lnrpc.AddInvoiceResponse{
3246+
PaymentRequest: hodlInv.payReq,
3247+
},
3248+
withGroupKey(groupID),
3249+
withFailure(lnrpc.Payment_IN_FLIGHT, failureNone),
3250+
)
3251+
3252+
logBalance(t.t, nodes, assetID, "after inflight multi-rfq")
3253+
3254+
// TODO: assert minNumHtlcs after rebase
3255+
3256+
// Now let's cancel the invoice and assert that all inbound channels
3257+
// have cleared their HTLCs.
3258+
payHash := hodlInv.preimage.Hash()
3259+
_, err = fabia.InvoicesClient.CancelInvoice(
3260+
ctx, &invoicesrpc.CancelInvoiceMsg{
3261+
PaymentHash: payHash[:],
3262+
},
3263+
)
3264+
require.NoError(t.t, err)
3265+
3266+
assertNumHtlcs(t.t, dave, 0)
3267+
assertNumHtlcs(t.t, erin, 0)
3268+
assertNumHtlcs(t.t, yara, 0)
3269+
3270+
logBalance(t.t, nodes, assetID, "after cancelled hodl")
3271+
3272+
// Now let's create a normal invoice that will be settled once all the
3273+
// HTLCs have been received. This is only possible because the payer
3274+
// uses multiple bolt11 hop hints to reach the destination.
3275+
invoiceResp := createAssetInvoice(t.t, nil, fabia, 15_000, assetID)
3276+
3277+
payInvoiceWithSatoshi(
3278+
t.t, charlie, invoiceResp, withGroupKey(groupID),
3279+
)
3280+
3281+
logBalance(t.t, nodes, assetID, "after multi-rfq receive")
3282+
}
3283+
31293284
// testCustomChannelsStrictForwarding is a test that tests the strict forwarding
31303285
// behavior of a node when it comes to paying asset invoices with assets and
31313286
// BTC invoices with satoshis.

itest/litd_test_list_on_test.go

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,4 +114,9 @@ var allTestCases = []*testCase{
114114
test: testCustomChannelsDecodeAssetInvoice,
115115
noAliceBob: true,
116116
},
117+
{
118+
name: "test custom channels multi rfq",
119+
test: testCustomChannelsMultiRFQReceive,
120+
noAliceBob: true,
121+
},
117122
}

0 commit comments

Comments
 (0)