diff --git a/src/lib/db/cleanup.ts b/src/lib/db/cleanup.ts index 94d5995afe..39e044b0ec 100644 --- a/src/lib/db/cleanup.ts +++ b/src/lib/db/cleanup.ts @@ -164,7 +164,7 @@ export async function cleanupCompressionAnalytics(): Promise { } /** - * Clean up old mcp_audit_log based on retention settings. + * Clean up old mcp_tool_audit based on retention settings. */ export async function cleanupMcpAudit(): Promise { const db = getDbInstance(); @@ -178,15 +178,15 @@ export async function cleanupMcpAudit(): Promise { const result: CleanupResult = { deleted: 0, errors: 0 }; try { - const stmt = db.prepare("DELETE FROM mcp_tool_audit WHERE timestamp < ?"); + const stmt = db.prepare("DELETE FROM mcp_tool_audit WHERE created_at < ?"); const runResult = stmt.run(cutoffISO); result.deleted = runResult.changes; console.log( - `[Cleanup] Deleted ${result.deleted} mcp_audit_log older than ${retentionDays} days` + `[Cleanup] Deleted ${result.deleted} mcp_tool_audit older than ${retentionDays} days` ); } catch (err: unknown) { - console.error("[Cleanup] Error cleaning mcp_audit_log:", err); + console.error("[Cleanup] Error cleaning mcp_tool_audit:", err); result.errors++; } @@ -194,7 +194,7 @@ export async function cleanupMcpAudit(): Promise { } /** - * Clean up old a2a_events based on retention settings. + * Clean up old a2a_task_events based on retention settings. */ export async function cleanupA2aEvents(): Promise { const db = getDbInstance(); @@ -208,13 +208,13 @@ export async function cleanupA2aEvents(): Promise { const result: CleanupResult = { deleted: 0, errors: 0 }; try { - const stmt = db.prepare("DELETE FROM a2a_task_events WHERE timestamp < ?"); + const stmt = db.prepare("DELETE FROM a2a_task_events WHERE created_at < ?"); const runResult = stmt.run(cutoffISO); result.deleted = runResult.changes; - console.log(`[Cleanup] Deleted ${result.deleted} a2a_events older than ${retentionDays} days`); + console.log(`[Cleanup] Deleted ${result.deleted} a2a_task_events older than ${retentionDays} days`); } catch (err: unknown) { - console.error("[Cleanup] Error cleaning a2a_events:", err); + console.error("[Cleanup] Error cleaning a2a_task_events:", err); result.errors++; } diff --git a/tests/unit/cleanup-column-fix.test.mjs b/tests/unit/cleanup-column-fix.test.mjs index eeb3aeafd9..7dd4330c85 100644 --- a/tests/unit/cleanup-column-fix.test.mjs +++ b/tests/unit/cleanup-column-fix.test.mjs @@ -112,3 +112,29 @@ test("cleanup: memories uses correct table name (not 'memory_entries')", () => { "must NOT use non-existent table name memory_entries" ); }); + +test("cleanup: mcp_tool_audit prunes by created_at (existing column), not timestamp", () => { + // mcp_tool_audit has created_at (see 002_mcp_a2a_tables.sql); timestamp does + // not exist, so WHERE timestamp < ? raised SqliteError "no such column" at + // every boot-time cleanup and the retention pruning never ran. + assert.ok( + source.includes("DELETE FROM mcp_tool_audit WHERE created_at < ?"), + "mcp_tool_audit cleanup must use created_at column" + ); + assert.ok( + !source.includes("DELETE FROM mcp_tool_audit WHERE timestamp"), + "must NOT use timestamp for mcp_tool_audit (column doesn't exist)" + ); +}); + +test("cleanup: a2a_task_events prunes by created_at (existing column), not timestamp", () => { + // Same schema fact for a2a_task_events (created_at, no timestamp column). + assert.ok( + source.includes("DELETE FROM a2a_task_events WHERE created_at < ?"), + "a2a_task_events cleanup must use created_at column" + ); + assert.ok( + !source.includes("DELETE FROM a2a_task_events WHERE timestamp"), + "must NOT use timestamp for a2a_task_events (column doesn't exist)" + ); +});