From 43bd529b78dba2b0c43ba85d33c394b6fd4af186 Mon Sep 17 00:00:00 2001 From: Kfir Amar Date: Sat, 14 Mar 2026 22:18:41 +0200 Subject: [PATCH] fix(db): add provider connection group migration Add the missing provider_connections.group column to both the base schema and the runtime column backfill path. Also add a regression test covering upgrade from an older database that does not yet have the column. --- src/lib/db/core.ts | 5 ++++ tests/unit/fixes-p1.test.mjs | 57 ++++++++++++++++++++++++++++++++++++ 2 files changed, 62 insertions(+) diff --git a/src/lib/db/core.ts b/src/lib/db/core.ts index 7a433f3fff..178ceade45 100644 --- a/src/lib/db/core.ts +++ b/src/lib/db/core.ts @@ -80,6 +80,7 @@ const SCHEMA_SQL = ` consecutive_use_count INTEGER DEFAULT 0, rate_limit_protection INTEGER DEFAULT 0, last_used_at TEXT, + "group" TEXT, created_at TEXT NOT NULL, updated_at TEXT NOT NULL ); @@ -316,6 +317,10 @@ function ensureProviderConnectionsColumns(db: SqliteDatabase) { db.exec("ALTER TABLE provider_connections ADD COLUMN last_used_at TEXT"); console.log("[DB] Added provider_connections.last_used_at column"); } + if (!columnNames.has("group")) { + db.exec('ALTER TABLE provider_connections ADD COLUMN "group" TEXT'); + console.log('[DB] Added provider_connections."group" column'); + } } catch (error: unknown) { const message = error instanceof Error ? error.message : String(error); console.warn("[DB] Failed to verify provider_connections schema:", message); diff --git a/tests/unit/fixes-p1.test.mjs b/tests/unit/fixes-p1.test.mjs index 95b1f91186..5b6445a135 100644 --- a/tests/unit/fixes-p1.test.mjs +++ b/tests/unit/fixes-p1.test.mjs @@ -141,6 +141,63 @@ test("provider connection persists rateLimitProtection across reopen", async () assert.equal(secondRead.rateLimitProtection, true); }); +test('provider connection migration adds "group" column for existing databases', async () => { + await resetStorage(); + + const sqlitePath = core.SQLITE_FILE; + core.resetDbInstance(); + + const Database = (await import("better-sqlite3")).default; + const db = new Database(sqlitePath); + db.exec(` + CREATE TABLE provider_connections ( + id TEXT PRIMARY KEY, + provider TEXT NOT NULL, + auth_type TEXT, + name TEXT, + email TEXT, + priority INTEGER DEFAULT 0, + is_active INTEGER DEFAULT 1, + access_token TEXT, + refresh_token TEXT, + expires_at TEXT, + token_expires_at TEXT, + scope TEXT, + project_id TEXT, + test_status TEXT, + error_code TEXT, + last_error TEXT, + last_error_at TEXT, + last_error_type TEXT, + last_error_source TEXT, + backoff_level INTEGER DEFAULT 0, + rate_limited_until TEXT, + health_check_interval INTEGER, + last_health_check_at TEXT, + last_tested TEXT, + api_key TEXT, + id_token TEXT, + provider_specific_data TEXT, + expires_in INTEGER, + display_name TEXT, + global_priority INTEGER, + default_model TEXT, + token_type TEXT, + consecutive_use_count INTEGER DEFAULT 0, + rate_limit_protection INTEGER DEFAULT 0, + last_used_at TEXT, + created_at TEXT NOT NULL, + updated_at TEXT NOT NULL + ) + `); + db.close(); + + const reopened = core.getDbInstance(); + const columns = reopened.prepare("PRAGMA table_info(provider_connections)").all(); + const names = new Set(columns.map((column) => column.name)); + assert.equal(names.has("group"), true); +}); + test("resolveProxyForConnection applies combo proxy for object/string model entries", async () => { await resetStorage();