fix(insights): add ensureInsightRunsSchemaCompatibility for missing lifecycle column

Databases already at schema v59+ when the lifecycle column was added never
re-ran the v59 migration, causing "no column named lifecycle" errors on
insight generation. Adds an unconditional compatibility check following the
existing ensureRoutinesSchemaCompatibility pattern.

Fixes #42

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Timothy Laurent
2026-05-05 11:31:21 -07:00
parent 1f50be85a1
commit 46c6b7a59a

View File

@@ -1003,6 +1003,7 @@ export class Database {
// Compatibility backfills that must run even when schemaVersion is current.
this.ensureRoutinesSchemaCompatibility();
this.ensureInsightRunsSchemaCompatibility();
// Seed config row idempotently with default settings
const configNow = new Date().toISOString();
@@ -1057,6 +1058,25 @@ export class Database {
this.db.exec("CREATE INDEX IF NOT EXISTS idxRoutinesScope ON routines(scope)");
}
/**
* Applies idempotent compatibility fixes for the project_insight_runs table.
*
* The `lifecycle` and `cancelledAt` columns were added to SCHEMA_SQL and
* retroactively inserted into migration v33's CREATE TABLE, with a safety-net
* in migration v59. However, databases that were already at v59+ when the
* commit landed never re-run v59, leaving the columns missing. Running this
* unconditionally on every init guarantees the columns exist.
*/
private ensureInsightRunsSchemaCompatibility(): void {
if (!this.hasTable("project_insight_runs")) {
return;
}
this.addColumnIfMissing("project_insight_runs", "lifecycle", "TEXT");
this.addColumnIfMissing("project_insight_runs", "cancelledAt", "TEXT");
this.db.exec(`CREATE INDEX IF NOT EXISTS idxInsightRunsProjectTriggerStatus ON project_insight_runs(projectId, trigger, status)`);
}
private migrate(): void {
const version = this.getSchemaVersion() || 1;