Commit Graph

65 Commits

Author SHA1 Message Date
Elle Mouton
0607982886 graph/db: implement ForEachNodeDirectedChannel and ForEachNodeCacheable
Here we add the `ForEachNodeDirectedChannel` and `ForEachNodeCacheable`
SQLStore implementations which then lets us run
`TestGraphTraversalCacheable` and `TestGraphCacheForEachNodeChannel`
against SQL backends.
2025-06-18 16:55:00 +02:00
Elle Mouton
8af32951c7 graph/db+sqldb: implement ForEachNode
In this commit the `ForEachNode` method is added to the SQLStore. With
this, the `TestGraphCacheTraversal` unit test can be run against SQL
backends.
2025-06-18 16:54:59 +02:00
Elle Mouton
d60761f79c graph/db: fix error check in test
An error in TestChanUpdatesInHorizon was previously not checked
correctly.
2025-06-18 15:24:16 +02:00
Elle Mouton
f89e3ceced graph/db+sqldb: implement ForEachSourceNodeChannel
In this commit, the ForEachSourceNodeChannel implementation of the
SQLStore is added. Since this is the first method of the SQLStore that
fetches channel and policy info, it also adds all the helpers that are
required to do so. These will be re-used in upcoming commits as more
"For"-type methods are added.

With this implementation, we convert the `TestForEachSourceNodeChannel`
such that it is run against SQL backends.
2025-06-18 08:43:56 +02:00
Elle Mouton
e724e1c3e4 multi: thread context through to AddrsForNode 2025-06-17 19:20:59 +02:00
Elle Mouton
d1fa5701eb graph/db: thread context through to DeleteLightningNode 2025-06-17 19:20:59 +02:00
Elle Mouton
dc6259fcc3 graph/db: thread context through to HasLightningNode 2025-06-17 19:20:56 +02:00
Elle Mouton
66c5a97202 graph/db: thread context through to FetchLightingNode 2025-06-17 19:20:27 +02:00
Elle Mouton
d1cfb47428 graph/db: thread context to AddLightningNode 2025-06-17 19:20:27 +02:00
Elle Mouton
c327988bb3 graph/db+sqldb: implement UpdateEdgePolicy
In this commit, the various SQL queries are defined that we will need in
order to implement the SQLStore UpdateEdgePolicy method. Channel
policies can be "replaced" and so we use the upsert pattern for them
with the rule that any new channel policy must have a timestamp greater
than the previous one we persisted.

As is done for the KVStore implementation of the method, we use the
batch scheduler for this method.
2025-06-17 13:43:07 +02:00
Elle Mouton
239acb4063 graph/db: validate edge policy TLV data before persisting
In this commit, we start validating the extra opaque data of a channel
edge policy before persisting it. We just check that the data is valid
TLV.

NOTE: we recently [started
validating](1410a0949d)
this at the lnwire level. So really, no new update will reach the DB
layer without this already being checked. But we check it again here so
that the DB API behaves correctly as its own unit.
2025-06-09 08:26:11 +02:00
Elle Mouton
547b836180 sqldb+graph/db: fix UpsertNode bug
Account for the last_update field being null.
2025-06-02 17:29:03 +02:00
Elle Mouton
eb32b39380 graph/db: demonstrate SQL upsert node bug 2025-06-02 17:28:59 +02:00
Elle Mouton
cf542458bd graph/db+sqldb: add HighestChanID to SQLStore 2025-06-02 14:53:18 +02:00
Elle Mouton
d93d104a66 graph/db+sqldb: implement AddChannelEdge on SQLStore
In this commit, the `AddChannelEdge` method of the SQLStore is
implemented. Like the KVStore implementation, it makes use of the
available channel `batch.Scheduler` and also updates the reject and
channel caches.

This then lets us convert the following 2 unit tests to run against the
SQL backends:
- TestPartialNode
- TestAddChannelEdgeShellNodes
2025-06-02 14:53:18 +02:00
Elle Mouton
c5f159f485 graph/db: expand AddChannelEdge test
Expand the existing TestAddChannelEdgeShellNodes test so that we have
coverage for error we expect when AddChannelEdge is called a second time
if we already know of a channel.
2025-06-02 14:53:18 +02:00
Elle Mouton
2a36e17f6f graph/db: only init extra byte if not nil
In preparation for having consistency with the structs created by the
SQLStore and the KVStore (so that they have the same behaviour when
tested by the unit tests), here we make sure not to init the
ExtraOpaqueData field of the LightningNode struct unless there are
actualy bytes to set.
2025-06-02 14:53:18 +02:00
Elle Mouton
0064d33cda sqldb+graph/db: source nodes table, queries and CRUD
In this commit, we add the `source_nodes` table. It points to entries in
the `nodes` table. This table will store one entry per protocol version
that we are announcing a node_announcement on.

With this commit, we can run the TestSourceNode unit test against our
SQL backends.
2025-05-27 18:36:59 +02:00
Elle Mouton
86d48390ca sqldb+graph/db: implement SQLStore.NodeUpdatesInHorizon
In this commit we add the necessary SQL queries and then implement the
SQLStore's NodeUpdatesInHorizon method. This lets us run the
TestNodeUpdatesInHorizon unit tests against SQL backends.
2025-05-27 18:36:59 +02:00
Elle Mouton
7a120cb584 graph/db: implement SQLStore.LookupAlias
In this commit, we let the SQLStore implement LookupAlias. This then
lets us run the TestAliasLookup unit test against the SQL backends.
2025-05-27 18:36:59 +02:00
Elle Mouton
d1f7cce68b sqldb+graphdb: SQL methods for Node CRUD
In this commit, we add the various sqlc queries that we need in order
to implement the following V1Store methods:

- AddLightningNode
- FetchLightningNode
- HasLightningNode
- AddrsForNode
- DeleteLightningNode
- FetchNodeFeatures

These are implemented by SQLStore which then lets us use the SQLStore
backend for the following unit tests:

- TestNodeInsertionAndDeletion
- TestLightningNodePersistence
2025-05-27 18:36:59 +02:00
Elle Mouton
14ca086c72 graph/db: skip TestGraphLoading for non-bbolt store
Let all the NewTestDB functions return the V1Store interface type
instead of pointers. Then add a manual skip in the TestGraphLoading test
for any non-bbolt backend. We can remove this once all the methods used
by the test have been implemented by the SQLStore. We only need the
manual skip for this one test since it is the only one that doesnt use
MakeGraphTest to init the graph db.
2025-05-23 10:53:27 +02:00
Elle Mouton
9b9a964975 graph/db: more test coverage for node addresses
In this commit we add more test coverage for the persistence of the
addresses of a LightningNode. This is so that we have unit test coverage
that ensures that all the various address types can be persisted and
that the order of the addresses (within a type) are preserved.
2025-05-22 14:14:42 +02:00
Elle Mouton
629e74a53c graph/db: add various error assertions
Here we expand TestEdgeInsertionDeletion to assert that the expected
error is returned when AddChannelEdge is called for a channel that has
already been persisted. We also take the opportunity to convert some of
the error checks in the test to use strict error type matching.

Finally, we test that the expected error is returned if
DeleteLightningNode is called for a node that is no longer in the DB.
2025-05-22 14:14:42 +02:00
Elle Mouton
3bc58a0d2f graph/db: test the non-cached version of ForEachNodeDirectedChannel
Expand an existing test for ForEachNodeDirectedChannel so that it also
tests the DB method and not just the ChannelGraph method which will use
the in-memory graph cache for the query.
2025-05-22 14:14:42 +02:00
Elle Mouton
b285546ce1 graph/db: add NewTestDB method
In this commit, we add a `test_kvdb.go` file with a single definition of
the `NewTestDB` function. A new version of `MakeTestGraph` (called
`MakeTestGraphNew` is added which makes use of this `NewTestDB` function
to create the backing `V1Store` passed to the `ChannelGraph` for tests.

Later on, we will add new implementations of this method backed by
sqlite and postgres.  When those are added, then build flags will
control which version of `NewTestDB` is called.

With this change, the only test call-site of `NewKVStore` is the new
`test_kvdb.go` file.
2025-05-22 14:14:42 +02:00
Elle Mouton
4233649e6a graph/db: let MakeTestGraph require no error internally
Instead of returning an error and needing to call `require.NoError` for
each call to `MakeTestGraph`, rather just used the available testing
variable to require no error within the function itself.
2025-05-22 14:14:41 +02:00
Elle Mouton
44a92b7efe graph/db: add test coverage for AddEdgeProof 2025-05-22 14:14:41 +02:00
Elle Mouton
3dfc1725d8 graph/db: use mainnet genisis hash in tests
In preparation for our SQL Graph store which wont explicitly store the
chain hash but will instead obtain it from the runtime config, we
replace the test chainhash value with that of the mainnet genesis hash.
2025-05-22 14:14:41 +02:00
Elle Mouton
a9e64542c1 graph/db: set empty Features and ExtraOpaqueData in tests
So we can use`require.Equal` for the ChannelEdgeInfo type.
2025-05-22 14:14:41 +02:00
Elle Mouton
95220b7102 graph/db: check for wrapped errors
In preparation for a different store impl which may wrap errors, we
use `require.ErrorIs` for error assertions rather than direct "="
comparisons in tests.
2025-05-22 14:14:41 +02:00
Elle Mouton
227e49d0ae graph/db: expand TestNodeInsertionAndDeletion
Expand this existing test so that it also tests that a node's addresses
and feature are fetched correctly after insertion. With this, we ensure
that the `FetchNodeFeatures` and `AddrsForNodes` methods of the
`V1Store` interface are properly covered by unit tests.
2025-05-22 14:14:41 +02:00
Elle Mouton
0db91304cf graph/db: make all ExtraOpaqueData valid TLV streams
Later when we introduce our SQL version of the graph store, we will
normalise the persistence of the ExtraOpaqueData using the fact that it
is always made up of TLV entries. So we update our tests here to ensure
that they use valid TLV streams as examples.
2025-05-22 14:14:40 +02:00
Elle Mouton
526fb7f181 graph/db: init KVStore outside of ChannelGraph
So that we can pass in the abstract V1Store in preparation for adding a
SQL implementation of the KVStore.
2025-05-22 14:14:40 +02:00
Elle Mouton
449684de87 graph/db: use V1Store interface in ChannelGraph
Use the new `V1Store` interface as a field in the `ChannelGraph` rather than
a pointer to the `KVStore` implementation in preparation for allowing a
SQL implementation of `V1Store` to be used by the `ChannelGraph`.

Note that two tests are adjusted in this commit to be skipped if the
V1Store is not the `KVStore` implementation since the tests are very
bbolt specific.
2025-05-22 14:14:40 +02:00
Elle Mouton
258dd12cb2 graph/db: update the compareNodes helper
- Let it do a proper comparison of the full structs passed in.
- Pass in a testing parameter so we can remove the returned error.
- Make sure the callers are passing in the expected and result
  parameters in the correct order.
- Fix a bug: the compareNodes was not comparing the Features field of
  the LightningNode structs. Now that it does, one test needed to be
updated to properly set the expected Features fields.
2025-05-22 14:14:40 +02:00
Elle Mouton
8468c7c4ba graph/db: let test alias be UTF-8 compatible
Later on we will store the Alias as a Text field in our sql impls of the
graph db. For Postgres, this field then MUST be a valid UTF-8 string.
This is also the case in general for the alias according to [bolt
7](e1fa25cf00/07-routing-gossip.md (L313))
2025-05-22 14:14:40 +02:00
Elle Mouton
da3deeee7c multi: remove kvdb.RTx from ForEachNodeChannel
Since we have not removed all call-sites that make use of this
parameter, we can remove it. This helps hide DB-specific details from
the interface we will introduce for the graph store.
2025-05-22 14:14:39 +02:00
Elle Mouton
3ec4798311 graph/db: use only exported KVStore methods in tests
Replace all calls to bbolt specific methods on the KVStore to instead
use exported methods on the KVStore that are more db-agnostic.
2025-05-22 14:14:39 +02:00
Elle Mouton
ea4b8c30a4 graph/db: unexport various methods that expose kvdb.RTx
Unexport the KVStore `FetchOtherNode` and `ForEachNodeChannelTx` methods
so that fewer exposed methods are leaking implementation details.
2025-05-22 14:14:39 +02:00
Elle Mouton
42e87396ec graph/db: introduce ForEachSourceNodeChannel
In preparation for creating a clean interface for the graph store, we
want to hide anything that is DB specific from the exposed methods on
the interface. Currently the `ForEachNodeChannel` and the
`FetchOtherNode` methods of the `KVStore` expose a `kvdb.RTx` parameter
which is bbolt specific. There is only one call-site of
`ForEachNodeChannel` actually makes use of the passed `kvdb.RTx`
parameter, and that is in the `establishPersistentConnections` method of
the `server` which then passes the tx parameter to `FetchOtherNode`.

So to clean-up the interface such that the `kvdb.RTx` is no longer
exposed: we instead create one new method called
`ForEachSourceNodeChannel` which can be used to replace the above
mentioned call-site. So as of this commit, all the remaining call-site
of `ForEachNodeChannel` pass in a nil param for `kvdb.RTx` - meaning we
can remove the parameter in a future commit.
2025-05-22 14:14:39 +02:00
Elle Mouton
2f54a0a26a graph/db: use only exported KVStore ForEachNode method in tests
Replace all tests calls to the private `forEachNode` method on the
`KVStore` with the exported ForEachNode method. This is in preparation
for having the tests run against an abstract DB backend.
2025-05-22 14:14:38 +02:00
Elle Mouton
b83b4015d9 graph/db: remove kvdb.Backend from test helpers
Remove unused kvdb.Backend param from `randEdgePolicy` and
`newEdgePolicy` test helpers.
2025-05-22 14:14:38 +02:00
Elle Mouton
5e3d66a97b graph/db: remove kvdb param from test helper
Remove the kvdb.Backend parameter from the `createChannelEdge` helper.
This is all in preparation for having the unit tests run against any DB
backend.
2025-05-22 14:14:37 +02:00
Elle Mouton
e2b592827e graph/db: test clean-up
This commit cleans up the graph test code by removing unused kvdb type
parameters from the `createTextVertex` and `createLightningNode` helper
methods. We also pass in the testing parameter now so that we dont need
to check the error each time we call `createTestVertex`.
2025-05-22 14:14:37 +02:00
Elle Mouton
2221aaa889 graph/db: move Topology client management to ChannelGraph
We plan to later on add an option for a remote graph source which will
be managed from the ChannelGraph. In such a set-up, a node would rely on
the remote graph source for graph updates instead of from gossip sync.
In this scenario, however, our topology subscription logic should still
notify clients of all updates and so it makes more sense to have the
logic as part of the ChannelGraph so that we can send updates we receive
from the remote graph.
2025-03-24 15:05:48 +02:00
Elle Mouton
4131b3fc7e graph/db: adjust TestPartialNode
The test as it stands today does not make sense as it adds a
Partial/Shell node to the graph via AddLightningNode which will never
happen since this is only ever triggered by the gossiper which only
calls the method with a full node announcement. Shell/Partial nodes are
only ever added via AddChannelEdge which will insert a partial node if
we are adding a channel edge which has node pub keys that we dont have a
node entry for. So we adjust the test to use this more accurate flow.
2025-03-24 15:05:48 +02:00
Elle Mouton
b497c4694e multi: add Start and Stop methods for ChannelGraph
We do this in preparation for moving channel cache population logic out
of the constructor and into the Start method. We also will later on
(when topology subscription is moved to the ChannelGraph), have a
goroutine that will need to be kicked off and stopped.
2025-03-24 15:05:47 +02:00
Elle Mouton
bb3839e422 graph/db: completely remove cache from KVStore 2025-03-24 15:05:47 +02:00
Elle Mouton
4d00eb2aa4 graph/db: move FilterKnownChanIDs zombie logic up one layer
Here, we move the business logic in FilterKnownChanIDs from the CRUD
layer to the ChannelGraph layer. We also add a test for the logic.
2025-03-24 15:05:47 +02:00