sqldb: add network-mismatch safeguard for native-SQL backends#10684
sqldb: add network-mismatch safeguard for native-SQL backends#10684ziggie1984 merged 7 commits intolightningnetwork:masterfrom
Conversation
d58fddd to
84fa870
Compare
Summary of ChangesHello, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed! This pull request introduces a safety mechanism to ensure that a database initialized for one Bitcoin network cannot be accidentally reused for another. By persisting the network identifier in a new metadata table during the first startup, the system can now detect and block incompatible configurations, providing clear error messages to the user instead of allowing silent data corruption. Highlights
🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console. Using Gemini Code AssistThe full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips. Invoking Gemini You can request assistance from Gemini at any point by creating a comment using either
Customization To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a Limitations & Feedback Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for GitHub and other Google products, sign up here. Footnotes
|
There was a problem hiding this comment.
Code Review
This pull request introduces a mechanism to prevent silent data corruption by ensuring that the database is not reused across different Bitcoin networks. It adds a metadata table to store the network name on first startup and validates it on subsequent restarts for both PostgreSQL and SQLite backends. Feedback was provided regarding the accuracy of a comment in config_builder.go and a suggestion to improve code organization by moving the BaseDB.ValidateNetwork implementation to interfaces.go.
84fa870 to
752ad80
Compare
309ee14 to
3e33be4
Compare
3041b52 to
02ec43f
Compare
b927793 to
5b917c4
Compare
|
@Roasbeef: review reminder |
| // networks) is not covered here because the itest harness does not provide a | ||
| // direct path to inject an existing SQLite file into a new node. The feature | ||
| // is exercised for SQLite at the unit-test level in | ||
| // sqldb/validate_network_test.go. |
There was a problem hiding this comment.
do you mean in chainparams/store_test.go.?
| func (s *Store) ValidateNetwork(ctx context.Context, | ||
| net *chaincfg.Params) error { | ||
|
|
||
| network := net.Name |
There was a problem hiding this comment.
worth checking Name isn't empty here.
Also should we use network := lncfg.NormalizeNetwork(net.Name) to collapse testnet3 to testnet?
| } | ||
|
|
||
| if storedNetwork != network { | ||
| return fmt.Errorf("%w: the database was "+ |
There was a problem hiding this comment.
I think the convention is to place the wrapped-error at the end, but I guess since ErrNetworkMismatch is produced here, it is fine.
| func (s *Store) ValidateNetwork(ctx context.Context, | ||
| net *chaincfg.Params) error { | ||
|
|
||
| network := net.Name |
| // Insert the network only if the chain_params table is | ||
| // still empty. This is a no-op on every startup after | ||
| // the first. | ||
| err := tx.InsertChainNetwork(ctx, network) |
There was a problem hiding this comment.
Alternatively we could let the foreign key error bubble up, then bail instead of the noop insert then check.
Non-blocking.
5b917c4 to
847fdff
Compare
|
Current network binding uses the normalized network name. This protects the standard networks and avoids cross-network reuse in the common case. It does not yet distinguish distinct custom signet networks that share the same signet name; strengthening chain identity for that case is left as follow-up work. |
PR Severity: CRITICAL
Critical (6 files):
Medium (4 files):
Low (1 file):
Analysis: This PR introduces a new SQL-backed chain_params store together with migration 000014, which creates a new database table. Per classification rules, all sqldb/* changes and especially any new migrations are automatically CRITICAL. The migration permanently alters the database schema, so it requires careful expert review to ensure:
No severity bump was applied: 11 non-excluded files (< 20) and ~220 lines changed (< 500), with a single distinct critical package (sqldb). To override, add a severity-override-{critical,high,medium,low} label. |
|
/gemini review |
There was a problem hiding this comment.
Code Review
This pull request introduces a mechanism to prevent silent data corruption by persisting and validating the Bitcoin network type within the SQL database. It adds a new chain_params table and a Store to manage network validation during startup for both Postgres and SQLite backends. A logic error was identified in config_builder.go where the network validation check could be bypassed if the migration skip flag for the inactive database backend was set, potentially leaving the safeguard disabled in certain configurations.
847fdff to
4066315
Compare
|
needs to be merged after #10726 |
4066315 to
b3f35b6
Compare
b3f35b6 to
def2f24
Compare
gijswijs
left a comment
There was a problem hiding this comment.
Apart from some nits, this thing LGTM!
Please fix the typo in the penultimate commit: ("release not" → "release note")
🎉
This is in particular important when running with a postgres backend. This only works if you run LND with the native sql flag but people should run it with this flag from 21 on anyways.
Skip the chain_params network check when startup is explicitly configured to skip SQL migrations. In that mode the schema is assumed to already be managed externally, and the chain_params table may not exist yet. Avoid failing startup on a missing table in this path.
def2f24 to
e744e19
Compare
This PR prevents silent data corruption that can occur when a user accidentally points lnd at a native-SQL database that was initialised for a different Bitcoin network.
Changes
A new
metadatatable (migration000014) stores a singlenetworkkey on first startup. On every subsequent restart, lnd reads that value and refuses to start if it doesn't match the configured network, printing a clear error message with remediation steps.The check is implemented on
BaseDBand applies to both the PostgreSQL and SQLite backends. The itest exercises the full startup-refusal path for PostgreSQL. Unit tests covering the mismatch and idempotent-match cases run against both backends via thetest_db_postgres || test_db_sqlitebuild tag.Fixes: #10354