11 KiB
作成
LocalTicketBackend によって作成されました。
State changed
Ticket を workspace-panel が queued にしました。
Decision
Routing decision: implementation_ready
Reason:
- Panel Queue により routing が明示的に許可され、Ticket は
queued。 - Ticket body / thread / relation / OrchestrationPlan / Orchestrator workspace state を確認した。blocking relation はなく、planning に戻す concrete missing information はない。
- 対象は single-Pod conversation View の text-like Item selection/copy に限定され、Panel row selection とは scope が分かれている。
- Tool/non-text Item と copy target は implementation-time decision として許容されており、binding invariants / acceptance criteria / escalation conditions が明確。
Evidence checked:
- Ticket body/thread: requirements、copy target、tool/non-text handling、acceptance criteria、non-goals、related work を確認。
- Ticket relations:
00001KV072V89と00001KV10SN02は related のみで blocker ではない。 - OrchestrationPlan: 既存 record なし。
- Orchestrator workspace:
/home/hare/Projects/yoi/.worktree/orchestrationは clean、f0de8413上。 - Visible Pods: implementation child Pod なし。Intake peer は routing blocker ではない。
- Bounded code map:
crates/tui/src/single_pod.rs、copy/clipboard abstraction、mouse/selection/key handling tests。
IntentPacket:
Intent:
- single-Pod TUI conversation View で User/System/Assistant など text-like Item の表示テキストを mouse drag で選択し、
yで copy、Escで clear できるようにする。
Binding decisions / invariants:
- 対象は single-Pod View Item text。Panel Ticket/Pod row selection は変更しない。
- terminal-native text selection preservation は non-goal。View drag は Yoi text selection として扱う。
- selected/copy text、selection state、clipboard diagnostics は Pod history / model context / session log / Ticket records に残さない。
- composer input、scroll、rewind picker、modal/popup、normal key handling と衝突させない。
- bare Panel row mouse selection semantics は regress させない。
- Tool/non-text Item handling と copy target は実装報告または decision comment に明示する。
Requirements / acceptance criteria:
- UserItem / SystemItem / AssistantItem text を drag selection できる。
- drag start/update/release 後に selection state が残り、View 上で highlight される。
Escで selection clear。yで selected text を copy し、selection clear。- text-like Item を跨いだ selection が deterministic separator で copy される。
- non-text/tool item handling decision が明示され、test で固定される。
- copy 成功/失敗が user-visible で、secret-like diagnostics を出さない。
- tests cover coordinate mapping、selection state、multi-item extraction、Esc、copy+clear、non-text/tool handling。
Implementation latitude:
- Existing clipboard abstraction があれば利用。なければ testable な最小 copy path を追加してよい。
- OSC52/system clipboard/internal copy buffer の選択は既存 TUI architecture に合わせる。
- rendering/highlight 表現、selection model の internal shape、separator は実装側判断。ただし deterministic にする。
Escalate if:
- terminal/crossterm event stream で必要な drag/release を識別できない。
- existing rendering model から text coordinate mapping を安全に取れない。
- copy target を追加すると secrets/history/model-context boundary に影響する。
- rewind/modal/composer key handling と共存できない大きな model change が必要。
Validation:
- focused
cargo test -p tui ...for single_pod selection/copy。 cargo check -p tui --all-targets。cargo fmt --check。git diff --check。- Panel row mouse selection regression test if related mouse plumbing is touched。
Critical risks / reviewer focus:
- selection/copy state の persistence leakage。
- mouse coordinate -> rendered text mapping correctness。
- multi-item extraction ordering/separator。
- composer/scroll/rewind/modal conflict。
- clipboard path safety and testability。
- Panel mouse behavior regression absence。
State changed
Routing decision と accepted implementation plan を記録済み。blocking relation / unresolved OrchestrationPlan blocker はなく、single-Pod View work は同時に開始する Panel composer work と主対象が異なるため、implementation side effects の前に queued -> inprogress acceptance を記録する。
Implementation report
Implementation report from Coder Pod yoi-coder-00001KV4YAAVY:
Commit:
09f5e9d5 feat: add single-pod text selection
Changed files:
crates/tui/src/text_selection.rs- New transient selection state, coordinate mapping, extraction, and focused tests.
crates/tui/src/app.rs- Local non-persistent selection state on
App.
- Local non-persistent selection state on
crates/tui/src/ui.rs- Selectable history row metadata, highlight rendering, snapshot wiring, selectable/non-text tests.
crates/tui/src/single_pod.rs- Drag mouse handling,
Escclear,ycopy+clear, OSC52 copy, tests.
- Drag mouse handling,
crates/tui/src/lib.rs- Module registration.
crates/tui/Cargo.toml,Cargo.lock- Added direct
base64dependency for OSC52 clipboard payloads.
- Added direct
Behavior / implementation decisions:
- Selectable Items:
UserMessageSystemMessageAssistantText
- Non-text/tool Items:
- tool calls, thinking, stats, greetings, alerts, turn headers, etc. are not selectable/copyable through this path.
- extraction skips non-selectable rows.
- Cross-item selection separator:
- copied text follows rendered row order and preserves selectable blank spacer rows, giving deterministic
\n\nbetween adjacent text-like Items.
- copied text follows rendered row order and preserves selectable blank spacer rows, giving deterministic
- Copy target:
- terminal clipboard via OSC52 (
ESC ] 52 ; c ; base64 BEL), not OS clipboard APIs. - avoids adding platform clipboard runtime behavior.
- terminal clipboard via OSC52 (
- Copy diagnostics:
- actionbar-only sanitized messages:
- success:
copied selected text to terminal clipboard - failure:
terminal clipboard write failed
- success:
- no selected content appears in diagnostics.
- actionbar-only sanitized messages:
- Selection persistence:
- selection state/copied text remains TUI-local only.
- not appended to Pod history, model context, session logs, Ticket records, memory, or durable state.
- Mouse tracking:
- single-Pod TUI now enables button-event drag tracking (
?1002h) but not all-motion tracking (?1003h). - Panel code was not changed.
- single-Pod TUI now enables button-event drag tracking (
Validation reported by coder:
- Passed:
cargo fmt --check - Passed:
cargo check -p tui --all-targets - Passed:
cargo test -p tui text_selection - Passed:
cargo test -p tui single_pod::tests - Passed:
cargo test -p tui ui::tests::history_rows_mark_text_items_selectable_and_non_text_unselectable - Passed:
git diff --check
Repository status:
- Child implementation worktree clean after commit.
Residual risks / notes:
- OSC52 clipboard success means sequence written/flushed; actual clipboard acceptance depends on terminal/multiplexer policy.
- No real PTY/E2E validation was run; coverage is focused unit-level mouse/key/selection/render extraction behavior.
Review: approve
Review result: approve
Evidence checked:
- Reviewed child worktree only:
/home/hare/Projects/yoi/.worktree/00001KV4YAAVY-single-pod-text-selection- diff
368249d6..09f5e9d5 - Ticket record/thread in the child worktree
- Read-only validation:
- Passed:
git diff --check 368249d6..09f5e9d5
- Passed:
Implementation review:
- TUI-local selection state was added in
crates/tui/src/text_selection.rsand wired into single-Pod rendering/input. - Mouse drag maps terminal coordinates through
HistoryViewportinto rendered history rows. - Drag start/update/release are handled in
single_pod.rs; selection remains active after release. Escclears selection before normal composer handling.- bare
ycopies only when a selection exists; otherwise composer input remains available. - Highlighting is applied through
range_for_rowandhighlight_line_selection. - Selectable item boundary is explicit:
- selectable:
UserMessage,SystemMessage,AssistantText - non-selectable: tool calls, thinking, notices, stats, greetings, etc.
- selectable:
- Tool/non-text rows are marked unselectable and extraction skips unselectable rows.
- Cross-item extraction is deterministic, with documented newline/blank-line behavior.
- Copy uses OSC52; selected text is base64 encoded before writing the OSC52 sequence.
- Copy diagnostics are generic/actionbar-local and do not include selected content.
- Selection state lives in TUI-local
App.text_selection; no path was found that appends selected/copied text to Pod history, model context, session log, Ticket records, memory, or durable state. - Mouse capture changes are limited to single-Pod fullscreen setup and avoid all-motion
?1003h; Panel/multi-pod mouse row selection code was not modified. - Composer, scroll, rewind picker, completion/key routing, and normal key handling interactions were inspected and no blocker found.
Coverage reviewed:
- coordinate mapping
- drag update/release state
- multi-row / separator extraction
- non-selectable row skipping
- Esc clear
- copy helper + clear
- UI selectable/non-selectable marking
- mouse capture mode avoiding all-motion tracking
Non-blocking notes:
- No PTY/E2E validation was run; terminal-specific OSC52/mouse behavior still depends on real terminal behavior.
- OSC52 cannot acknowledge terminal clipboard acceptance; implementation can only report write/flush success/failure.
- There is no explicit byte-size cap on OSC52 payload, but selection is bounded by visible rendered viewport rather than arbitrary full history traversal. Future hard cap/error notice would be reasonable hardening.
- A full fixture test constructing an actual
Block::ToolCallcould strengthen coverage, but the non-text path is explicit and source-inspected.
Validation not rerun by reviewer:
- Cargo validation was not rerun because review scope was read-only and Cargo writes build artifacts. Coder-reported validation was inspected as evidence.
Conclusion:
- Approved. No blocker remains.