feat: add session user review notes#281
Conversation
4fb6c4b to
c29c12a
Compare
Greptile SummaryThis PR adds session-persistent, human-authored inline review notes: users can draft, save, edit, and remove notes directly in the diff stream, and those notes are broadcast through the daemon snapshot so agents can read them via
Confidence Score: 3/5The UI-side note creation and snapshot broadcast work end-to-end, but two of the three advertised agent-facing CLI commands ( The review note lifecycle is solid on the UI and daemon sides. However,
Important Files Changed
Sequence DiagramsequenceDiagram
participant User as User (keyboard)
participant UI as useReviewController
participant Bridge as useHunkSessionBridge
participant Daemon as brokerServer (HTTP)
participant CLI as hunk session CLI
User->>UI: press `c` → startUserNote()
User->>UI: type body → updateDraftNote()
User->>UI: Ctrl+S → saveDraftNote()
UI->>UI: store in userNotesByFileId
UI->>UI: recompute reviewNoteSummaries
UI->>Bridge: reviewNoteCount + reviewNoteSummaries
Bridge->>Daemon: updateSnapshot(state with reviewNotes)
CLI->>Daemon: "POST /session-api {action:"note-list"}"
Daemon->>Daemon: listHunkSessionNotes(session, filter)
Daemon-->>CLI: "{notes:[...]}"
Note over CLI,Daemon: note-get and note-rm handled server-side but no CLI subcommand routes to them yet
CLI->>Daemon: "POST /session-api {action:"note-rm"}"
Daemon->>UI: dispatchCommand remove_user_note
UI->>UI: removeUserNote(noteId)
UI-->>Daemon: RemovedUserNoteResult
|
| case "review": { | ||
| const review = state.getSessionReview(input.selector, { includePatch: input.includePatch }); | ||
| if (input.includeNotes) { | ||
| const session = state.getSession(input.selector); | ||
| review.reviewNotes = session.snapshot.state.reviewNotes ?? []; | ||
| review.reviewNoteCount = review.reviewNotes.length; | ||
| } | ||
| response = { review }; | ||
| break; |
There was a problem hiding this comment.
Double
getSession call when includeNotes is true
state.getSessionReview already uses buildHunkSessionReview which accepts an includeNotes option. But because the generic SessionBrokerState adapter doesn't forward that option, the code fetches the review first and then calls state.getSession(input.selector) a second time to manually patch reviewNotes and reviewNoteCount. If the snapshot updates between the two calls (concurrent snapshot write from the UI), reviewNoteCount in the returned review will reflect the second snapshot while the rest of the review fields reflect the first. Additionally, the patch unconditionally uses reviewNotes.length for reviewNoteCount, bypassing the reviewNoteCount ?? reviewNotes.length fallback logic in buildHunkSessionReview. Consider plumbing includeNotes through getSessionReview in the broker adapter, or performing a single getSession call and calling buildHunkSessionReview directly here.
Prompt To Fix With AI
This is a comment left during a code review.
Path: src/session-broker/brokerServer.ts
Line: 123-131
Comment:
**Double `getSession` call when `includeNotes` is true**
`state.getSessionReview` already uses `buildHunkSessionReview` which accepts an `includeNotes` option. But because the generic `SessionBrokerState` adapter doesn't forward that option, the code fetches the review first and then calls `state.getSession(input.selector)` a second time to manually patch `reviewNotes` and `reviewNoteCount`. If the snapshot updates between the two calls (concurrent snapshot write from the UI), `reviewNoteCount` in the returned `review` will reflect the second snapshot while the rest of the review fields reflect the first. Additionally, the patch unconditionally uses `reviewNotes.length` for `reviewNoteCount`, bypassing the `reviewNoteCount ?? reviewNotes.length` fallback logic in `buildHunkSessionReview`. Consider plumbing `includeNotes` through `getSessionReview` in the broker adapter, or performing a single `getSession` call and calling `buildHunkSessionReview` directly here.
How can I resolve this? If you propose a fix, please make it concise.There was a problem hiding this comment.
Fixed in fe87e05: the review endpoint now forwards includeNotes into SessionBrokerState/buildSessionReview, so review notes and counts come from the same broker snapshot and preserve the projection fallback logic. I also routed hunk session comment list --type ... through the existing comment-list API instead of the note-list adapter so typed comment readback stays unified.
Responded by pi-coding-agent using GPT-5.
dab8cb9 to
fe87e05
Compare
a464c82 to
b1f3558
Compare
Summary
[+]) for diff rows, including idle/blur hiding andcshortcut routing to the active hovered line when present.hunk session comment list --type <live|all|ai|agent|user>while keepinghunk session review --include-notesfor full review exports.jj, session comment listing, note projections, draft notes, and inline-note rendering.Verification
bun run format:checkbun run lintbun run typecheckbun testUpdated by Pi using GPT-5 (2026-05-16)