1from pyln.client import Gossmap, GossmapNode, GossmapNodeId 2 3import os.path 4import lzma 5 6 7def unxz_data_tmp(src, tmp_path, dst, wmode): 8 fulldst = os.path.join(tmp_path, dst) 9 with open(fulldst, wmode) as out: 10 with lzma.open(os.path.join(os.path.dirname(__file__), "data", src), "rb")as f: 11 out.write(f.read()) 12 return fulldst 13 14 15def test_gossmap(tmp_path): 16 sfile = unxz_data_tmp("gossip_store-part1.xz", tmp_path, "gossip_store", "xb") 17 g = Gossmap(sfile) 18 19 chans = len(g.channels) 20 nodes = len(g.nodes) 21 22 g.refresh() 23 assert chans == len(g.channels) 24 assert nodes == len(g.nodes) 25 26 # Now append. 27 unxz_data_tmp("gossip_store-part2.xz", tmp_path, "gossip_store", "ab") 28 29 g.refresh() 30 31 # This actually deletes a channel, which deletes a node. 32 assert g.get_channel("686386x1093x1") is None 33 assert g.get_node('029deaf9d2fba868fe0a124050f0a13e021519a12f41bea34f391fe7533fb3166d') is None 34 # The other node is untouched 35 assert g.get_node('02e0af3c70bf42343316513e54683b10c01d906c04a05dfcd9479b90d7beed9129') 36 37 # It will notice the new ones. 38 assert chans < len(g.channels) 39 assert nodes < len(g.nodes) 40 41 # Whole load at the same time gives the same results. 42 g2 = Gossmap(sfile) 43 assert set(g.channels.keys()) == set(g2.channels.keys()) 44 assert set(g.nodes.keys()) == set(g2.nodes.keys()) 45 46 # Check some details 47 channel2 = g.get_channel("686200x1137x0") 48 assert g.get_channel("686386x1093x1") is None 49 assert channel2.satoshis == 3000000 50 51 52def test_gossmap_halfchannel(tmp_path): 53 """ this test a simple [l1->l2] gossip store that was created by the pyln-testing framework """ 54 sfile = unxz_data_tmp("gossip_store.simple.xz", tmp_path, "gossip_store", "xb") 55 g = Gossmap(sfile) 56 57 l1id = "022d223620a359a47ff7f7ac447c85c46c923da53389221a0054c11c1e3ca31d59" 58 l2id = "0266e4598d1d3c415f572a8488830b60f7e744ed9235eb0b1ba93283b315c03518" 59 60 # check structure parsed correctly 61 assert(len(g.nodes) == 2) 62 n1 = g.get_node(l1id) 63 n2 = g.get_node(l2id) 64 assert n1 65 assert n2 66 67 chan = g.get_channel("103x1x1") 68 assert chan 69 assert chan.node1 == n1 70 assert chan.node2 == n2 71 72 half0 = chan.get_direction(0) 73 half1 = chan.get_direction(1) 74 assert half0 75 assert half1 76 assert half0.direction == 0 77 assert half1.direction == 1 78 assert half0.channel == chan 79 assert half1.channel == chan 80 assert half0.source == n1 81 assert half0.destination == n2 82 assert half1.source == n2 83 assert half1.destination == n1 84 85 # check metadata 86 assert half0.timestamp == 1631005020 87 assert half1.timestamp == 1631005020 88 assert half0.cltv_expiry_delta == 6 89 assert half1.cltv_expiry_delta == 6 90 assert half0.htlc_minimum_msat == 0 91 assert half1.htlc_minimum_msat == 0 92 assert half0.htlc_maximum_msat == 990000000 93 assert half1.htlc_maximum_msat == 990000000 94 assert half0.fee_base_msat == 1 95 assert half1.fee_base_msat == 1 96 assert half0.fee_proportional_millionths == 10 97 98 99def test_objects(): 100 boltz = "026165850492521f4ac8abd9bd8088123446d126f648ca35e60f88177dc149ceb2" 101 acinq = "03864ef025fde8fb587d989186ce6a4a186895ee44a926bfc370e2c366597a3f8f" 102 103 boltz_id = GossmapNodeId(bytes.fromhex(boltz)) 104 acinq_id = GossmapNodeId(bytes.fromhex(acinq)) 105 assert boltz_id == GossmapNodeId(boltz) 106 107 assert boltz_id < acinq_id 108 assert acinq_id > boltz_id 109 assert boltz_id != acinq_id 110 assert acinq_id != boltz_id 111 assert not boltz_id > acinq_id 112 assert not acinq_id < boltz_id 113 assert not boltz_id == acinq_id 114 assert not acinq_id == boltz_id 115 116 boltz_node = GossmapNode(boltz_id) 117 acinq_node = GossmapNode(acinq_id) 118 assert boltz_node == GossmapNode(boltz) 119 assert boltz_node < acinq_node 120 assert acinq_node > boltz_node 121 assert boltz_node != acinq_node 122