Skip to content

feat: surface orphaned comments on removed files#279

Merged
tomasz-tomczyk merged 10 commits intomainfrom
feature/orphaned-comments
Apr 16, 2026
Merged

feat: surface orphaned comments on removed files#279
tomasz-tomczyk merged 10 commits intomainfrom
feature/orphaned-comments

Conversation

@tomasz-tomczyk
Copy link
Copy Markdown
Owner

Summary

  • When a file is added on a branch, receives review comments, and is then deleted, the comments were silently lost because the file vanishes from ChangedFiles(). Now the backend detects orphaned paths in the review file and creates phantom FileEntry objects with Orphaned: true.
  • Frontend renders phantom file sections with a "Removed" status badge, all comments (file + line-scoped) with an "Outdated" badge, and full resolve/edit/delete support using the existing comment CRUD path.
  • Orphan detection runs both on initial session load (loadCritJSON) and between rounds (restoreOrphanedComments in handleRoundCompleteGit/Files).

Test plan

  • Go unit tests: orphan detection, no-phantom for empty comments, idempotent restore, session info propagation
  • make test-diff includes orphaned comment scenario on the word-diff instance
  • golangci-lint clean, gofmt clean, CSS variable checker clean
  • CI: Go tests + E2E suite pass

🤖 Generated with Claude Code

tomasz-tomczyk and others added 10 commits April 16, 2026 11:29
When a file is added on a branch, receives review comments, and is then
deleted, the comments become invisible because the file vanishes from
the session. This spec designs phantom file sections that restore those
comments with outdated styling and full resolve/edit/delete support.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Add Orphaned field to FileEntry and SessionFileInfo. After restoring
comments for existing files in loadCritJSON, detect paths in the review
file that have comments but no matching session file, and create phantom
FileEntry objects with Status:"removed" and Orphaned:true.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Extract restoreOrphanedComments() helper that reads the review file and
creates phantom FileEntry objects for paths with comments not in the
session. Called from handleRoundCompleteGit and handleRoundCompleteFiles
after file list refresh and carry-forward, ensuring orphaned comments
survive across rounds.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Deduplicates the orphan-detection logic between loadCritJSON and
restoreOrphanedComments, bringing cyclomatic complexity below the
gocyclo threshold.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Skip content/diff fetches for orphaned files, only load comments
- Show phantom file sections with "Removed" badge and placeholder body
- Render all comments (file + line-scoped) in file-comments container
- Add "Outdated" badge and muted border/background to orphaned comments
- Disable "Add file-level comment" button on orphaned files
- Add "removed" status icon in file tree (gray with x)
- CSS variables in all 4 theme blocks for removed/outdated styling

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Adds a helpers.go file to the word-diff git instance, seeds comments
on it, then deletes the file and signals round-complete. The orphaned
comments should appear as a phantom section with "Removed" badge and
outdated styling.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
The left border treatment was foreign to the existing design system.
Instead, outdated comments now use reduced opacity (0.6, 0.85 on hover)
matching how resolved counts are dimmed. The "Outdated" badge uses the
same plain mono-text style as round badges. Removed unused --outdated-*
CSS variables from all 4 theme blocks.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
ClearAllComments (DELETE /api/comments) now filters out orphaned
FileEntry objects, preventing empty phantom sections from lingering
after E2E test cleanup.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@tomasz-tomczyk tomasz-tomczyk merged commit cad47c7 into main Apr 16, 2026
4 checks passed
@tomasz-tomczyk tomasz-tomczyk deleted the feature/orphaned-comments branch April 16, 2026 13:08
tomasz-tomczyk added a commit that referenced this pull request Apr 21, 2026
* feat: render outdated comments inline when lines leave diff hunks

When a reviewer comments on a diff line and the agent undoes that change,
the file stays in the diff but the commented lines disappear from hunks.
The comment existed in file.comments but had no inline anchor — invisible
except in the All Comments panel.

- Add appendOutdatedDiffComments() that detects unrendered comments after
  hunk rendering and shows them at the bottom of the diff section
- Uses existing outdated-comment/outdated-badge CSS classes (same as
  orphaned file comments from PR #279)
- Called from both renderDiffUnified and renderDiffSplit
- Full CRUD support: edit, delete, resolve all work on outdated comments

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix: add CSS for outdated-diff-comments container, remove unnecessary round-complete

- Add border-top and padding for .outdated-diff-comments section to
  visually separate it from diff hunks
- Remove unnecessary round-complete call in E2E test beforeEach (follows
  project convention — only clearAllComments needed)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix: use addComment helper, add guard against vacuous test passes

- Replace inline request.post calls with addComment from ./helpers (5 occurrences)
- Add expect(keys.size).toBeGreaterThan(0) guard in findNonHunkLine to
  prevent vacuous passes if diff API response shape doesn't match

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix: remove unrelated changes from other branch

Restore threading.spec.ts and activeReplyForms code that were
accidentally included from the fix/reply-form-font-size branch.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant