• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

lightningnetwork / lnd / 19338576814

13 Nov 2025 04:31PM UTC coverage: 65.209% (-0.01%) from 65.219%
19338576814

Pull #10367

github

web-flow
Merge ade491779 into f6005ed35
Pull Request #10367: multi: rename experimental endorsement signal to accountable

65 of 85 new or added lines in 11 files covered. (76.47%)

1775 existing lines in 24 files now uncovered.

137557 of 210947 relevant lines covered (65.21%)

20763.21 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

0.0
/itest/lnd_experimental_accountability.go
1
package itest
2

3
import (
4
        "math"
5

6
        "github.com/btcsuite/btcd/btcutil"
7
        "github.com/lightningnetwork/lnd/lnrpc"
8
        "github.com/lightningnetwork/lnd/lnrpc/routerrpc"
9
        "github.com/lightningnetwork/lnd/lntest"
10
        "github.com/lightningnetwork/lnd/lntest/node"
11
        "github.com/lightningnetwork/lnd/lntest/rpc"
12
        "github.com/lightningnetwork/lnd/lntest/wait"
13
        "github.com/lightningnetwork/lnd/lntypes"
14
        "github.com/lightningnetwork/lnd/lnwire"
15
        "github.com/stretchr/testify/require"
16
)
17

18
// testExperimentalAccountability tests setting of positive and negative
19
// experimental accountable signals.
NEW
20
func testExperimentalAccountability(ht *lntest.HarnessTest) {
×
NEW
21
        testAccountability(ht, true)
×
NEW
22
        testAccountability(ht, false)
×
23
}
×
24

25
// testAccountability sets up a 5 hop network and tests propagation of
26
// experimental accountable signals.
NEW
27
func testAccountability(ht *lntest.HarnessTest, aliceAccountable bool) {
×
28
        cfg := node.CfgAnchor
×
29
        carolCfg := append(
×
NEW
30
                []string{"--protocol.no-experimental-accountability"}, cfg...,
×
31
        )
×
32
        cfgs := [][]string{cfg, cfg, carolCfg, cfg, cfg}
×
33

×
34
        const chanAmt = btcutil.Amount(300000)
×
35
        p := lntest.OpenChannelParams{Amt: chanAmt}
×
36

×
37
        _, nodes := ht.CreateSimpleNetwork(cfgs, p)
×
38
        alice, bob, carol, dave, eve := nodes[0], nodes[1], nodes[2], nodes[3],
×
39
                nodes[4]
×
40

×
41
        bobIntercept, cancelBob := bob.RPC.HtlcInterceptor()
×
42
        defer cancelBob()
×
43

×
44
        carolIntercept, cancelCarol := carol.RPC.HtlcInterceptor()
×
45
        defer cancelCarol()
×
46

×
47
        daveIntercept, cancelDave := dave.RPC.HtlcInterceptor()
×
48
        defer cancelDave()
×
49

×
50
        req := &lnrpc.Invoice{ValueMsat: 1000}
×
51
        addResponse := eve.RPC.AddInvoice(req)
×
52
        invoice := eve.RPC.LookupInvoice(addResponse.RHash)
×
53

×
54
        sendReq := &routerrpc.SendPaymentRequest{
×
55
                PaymentRequest: invoice.PaymentRequest,
×
56
                TimeoutSeconds: int32(wait.PaymentTimeout.Seconds()),
×
57
                FeeLimitMsat:   math.MaxInt64,
×
58
        }
×
59

×
NEW
60
        expectedValue := []byte{lnwire.ExperimentalUnaccountable}
×
NEW
61
        if aliceAccountable {
×
NEW
62
                expectedValue = []byte{lnwire.ExperimentalAccountable}
×
NEW
63
                t := uint64(lnwire.ExperimentalAccountableType)
×
64
                sendReq.FirstHopCustomRecords = map[uint64][]byte{
×
65
                        t: expectedValue,
×
66
                }
×
67
        }
×
68

69
        _ = alice.RPC.SendPayment(sendReq)
×
70

×
71
        // Validate that our signal (positive or zero) propagates until carol
×
72
        // and then is dropped because she has disabled the feature.
×
NEW
73
        validateAccountableAndResume(ht, bobIntercept, true, expectedValue)
×
NEW
74
        validateAccountableAndResume(ht, carolIntercept, true, expectedValue)
×
NEW
75
        validateAccountableAndResume(ht, daveIntercept, false, nil)
×
76

×
77
        var preimage lntypes.Preimage
×
78
        copy(preimage[:], invoice.RPreimage)
×
79
        ht.AssertPaymentStatus(alice, preimage.Hash(), lnrpc.Payment_SUCCEEDED)
×
80
}
81

82
func validateAccountableAndResume(ht *lntest.HarnessTest,
83
        interceptor rpc.InterceptorClient, hasAccountable bool,
84
        expectedValue []byte) {
×
85

×
86
        packet := ht.ReceiveHtlcInterceptor(interceptor)
×
87

×
88
        var expectedRecords map[uint64][]byte
×
NEW
89
        if hasAccountable {
×
NEW
90
                u64Type := uint64(lnwire.ExperimentalAccountableType)
×
91
                expectedRecords = map[uint64][]byte{
×
92
                        u64Type: expectedValue,
×
93
                }
×
94
        }
×
95
        require.Equal(ht, expectedRecords, packet.InWireCustomRecords)
×
96

×
97
        err := interceptor.Send(&routerrpc.ForwardHtlcInterceptResponse{
×
98
                IncomingCircuitKey: packet.IncomingCircuitKey,
×
99
                Action:             routerrpc.ResolveHoldForwardAction_RESUME,
×
100
        })
×
101
        require.NoError(ht, err)
×
102
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc