From 4abbe2a226ca33585adaba8c5ebd6d8e5c06314d Mon Sep 17 00:00:00 2001 From: Taylor Eernisse Date: Mon, 26 Jan 2026 17:01:04 -0500 Subject: [PATCH] fix(ingest): Reset discussion watermarks when --full flag is used MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is a P1 fix from the CP1-CP2 alignment audit. The --full flag was designed to enable complete data re-synchronization, but it only reset sync_cursors for issues—it failed to reset the per-issue discussions_synced_for_updated_at watermark. The result was an inconsistent state: issues would be re-fetched from GitLab (because sync_cursors were cleared), but their discussions would NOT be re-synced (because the watermark comparison prevented it). This was a subtle bug because the watermark check uses: WHERE updated_at > COALESCE(discussions_synced_for_updated_at, 0) When discussions_synced_for_updated_at is already set to the issue's updated_at, the comparison fails and discussions are skipped. Fix: Before clearing sync_cursors, set discussions_synced_for_updated_at to NULL for all issues in the project. This makes COALESCE return 0, ensuring all issues become eligible for discussion sync. The ordering is important: watermarks must be reset BEFORE cursors to ensure the full sync behaves consistently. Co-Authored-By: Claude Opus 4.5 --- src/cli/commands/ingest.rs | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/src/cli/commands/ingest.rs b/src/cli/commands/ingest.rs index b7e309a..d752e2e 100644 --- a/src/cli/commands/ingest.rs +++ b/src/cli/commands/ingest.rs @@ -67,18 +67,26 @@ pub async fn run_ingest( // Get projects to sync let projects = get_projects_to_sync(&conn, &config.projects, project_filter)?; - // If --full flag is set, reset sync cursors for a complete re-fetch + // If --full flag is set, reset sync cursors and discussion watermarks for a complete re-fetch if full { println!( "{}", style("Full sync: resetting cursors to fetch all data...").yellow() ); for (local_project_id, _, path) in &projects { + // Reset discussion watermarks first so discussions get re-synced + conn.execute( + "UPDATE issues SET discussions_synced_for_updated_at = NULL WHERE project_id = ?", + [*local_project_id], + )?; + + // Then reset sync cursor conn.execute( "DELETE FROM sync_cursors WHERE project_id = ? AND resource_type = ?", (*local_project_id, resource_type), )?; - tracing::info!(project = %path, "Reset sync cursor for full re-fetch"); + + tracing::info!(project = %path, "Reset sync cursor and discussion watermarks for full re-fetch"); } }