feat(miner): add schema-version migration runner across local stores - #5347
feat(miner): add schema-version migration runner across local stores#5347real-venus wants to merge 1 commit into
Conversation
|
Superagent didn't find any vulnerabilities or security issues in this PR. |
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #5347 +/- ##
=======================================
Coverage 94.40% 94.41%
=======================================
Files 550 551 +1
Lines 44116 44135 +19
Branches 14631 14631
=======================================
+ Hits 41649 41668 +19
Misses 1792 1792
Partials 675 675
Flags with carried forward coverage won't be shown. Click here to find out more.
🚀 New features to boost your workflow:
|
|
Caution 🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥 🛑 Gittensory review result - reject/close recommendedReview updated: 2026-07-12 14:52:54 UTC
🛑 Suggested Action - Reject/Close
Review summary Blockers
Nits — 5 non-blocking
Why this is blocked
Linked issue satisfactionAddressed Review context
Contributor next steps
Signal definitions
[BETA] Chat with GittensoryAsk Gittensory a question about this PR directly in a comment — grounded only in the same cached, public-safe facts shown above, never a new claim.
Full command reference: https://gittensory.aethereal.dev/docs/gittensory-commands 🟩 Safe / merged · 🟦 Advisory · 🟨 Held for review · 🟥 Blocked / closed 💰 Earn for open-source contributions like this. Gittensor lets GitHub contributors earn for the work they already do — register to start earning →. Checked by Gittensory, a quiet PR intelligence layer for OSS maintainers.
|
|
An AI reviewer flagged a likely defect, but its confidence was below this repository's configured close-confidence floor, so this is held for a maintainer to confirm instead of closing automatically. Resolve the flagged defect (see the review notes), or ask a maintainer to override. |
The miner's local SQLite stores only ever ran CREATE TABLE IF NOT EXISTS, with no user_version/migration mechanism — so an older on-disk file was silently reused with a stale shape. Add a lightweight shared runner, applySchemaMigrations(db, migrations), and wire it into every store (claim-ledger, event-ledger, governor-ledger, plan-store, run-state, laptop-init, portfolio-queue). Each store's bootstrap schema is treated as version 1; a store's migrations array holds only post-baseline changes (migrations[i] upgrades version i+1 to i+2). The runner reads PRAGMA user_version, runs exactly the pending migrations in order, and stamps the new version, so opening an older file runs its outstanding migrations instead of continuing on an incompatible shape. Pre-versioning files (user_version 0) already carry the baseline tables, so they advance from the baseline. Kept lightweight per the issue — no heavyweight migration framework. Portfolio-queue's existing ad-hoc leased_at ALTER is expressed as its first real migration (1 to 2), staying defensive so a file that already ran the pre-convention ALTER is not re-altered into a duplicate-column error. Closes JSONbored#4832
d6d561a to
3db86a8
Compare
JSONbored
left a comment
There was a problem hiding this comment.
Closing:
packages/gittensory-miner/lib/schema-version.js:42 applies multiple migrations before stamping once at line 51, so if migration N succeeds and migration N+1 throws, the next open reruns migration N against an already-mutated schema and can fail permanently; wrap the migration loop and final `PRAGMA user_version` in one transaction, or stamp after each successful migration with a transaction around each migration plus its stamp.
…5378) gateVerdictReason() fell back to gate.summary for the top "Suggested Action" reason line -- but evaluateGateCheckCore's summary for a "failure" conclusion is literally gate.blockers restated as one joined string (title + action per finding). The "Why this is blocked" section a few lines below independently renders those SAME gate.blockers (folded in via buildDualReviewNotes), so every blocked/reject PR comment printed the identical blocker text twice. The existing test suite's gate() mock always hand-set a short generic summary ("A hard blocker was found."), never the realistic blockers-restated value evaluateGateCheckCore actually produces, so this never got caught locally -- it surfaced live on PR #5347. Only fall back to gate.summary/title when gate.blockers is empty (the neutral/held case, which has no "Why this is blocked" section to duplicate against and is the only state that still needs a top-level reason).
Summary
The miner's local SQLite stores only ever ran
CREATE TABLE IF NOT EXISTS, with nouser_version/migration mechanism at all — so an older on-disk database file was silently reused with a stale shape, unlike the main product'smigrations/discipline. This adds a lightweight, shared schema-versioning convention across every store.New:
packages/gittensory-miner/lib/schema-version.js(+.d.ts) exportingapplySchemaMigrations(db, migrations):BASELINE_SCHEMA_VERSION); a store'smigrationsarray holds only post-baseline changes —migrations[i]upgrades the schema from version i+1 to i+2.PRAGMA user_version, runs exactly the pending migrations in order, then stamps the new version — so opening an older file runs its outstanding migrations instead of continuing on an incompatible shape. Re-opening an up-to-date file runs none.user_version0) already carries the baseline tables (the idempotentCREATE TABLE IF NOT EXISTSran), so it advances from the baseline.DatabaseSynchandle — deterministic, no IO of its own beyond the PRAGMA read/write.Wired into all seven stores: claim-ledger, event-ledger, governor-ledger, plan-store, run-state, laptop-init, portfolio-queue.
Portfolio-queue's existing ad-hoc
leased_atALTER is expressed as its first real migration (1 → 2) — kept defensive (checkstable_info) so a version-0 file that already ran the pre-convention ad-hoc ALTER is not re-altered into a duplicate-column error. This both removes the ad-hoc branch and demonstrates the convention on a real migration.Kept lightweight per the issue's boundary — no heavyweight migration framework.
Scope
packages/), noblockedPaths, no secrets/private terms.d.tscompanion added, matching the package's existing conventionValidation
npm run typechecknpm run test:coverage(full unsharded suite)test/unit/miner-schema-version.test.ts(in-memoryDatabaseSync): baseline stamp with no migrations, full run in order on a pre-versioning file, idempotent re-apply, partial catch-up from an intermediate version, and coercion of an absent/non-integer/negativeuser_versionmainbaseline: identical results — the Windows-only chmod/path test failures are pre-existing and unrelated); portfolio-queue'sleased_at/markFailedtests confirm the migrated behavior is preservedSafety
user_versionstamp and a migration hook; the only converted logic (portfolio-queueleased_at) keeps its exact defensive semanticsCloses #4832