Skip to content

fix: track opencode session switches - #2455

Merged
ogulcancelik merged 2 commits into
masterfrom
akbash/2450-opencode-session-switch
Aug 10, 2026
Merged

fix: track opencode session switches#2455
ogulcancelik merged 2 commits into
masterfrom
akbash/2450-opencode-session-switch

Conversation

@akbash-bot

@akbash-bot akbash-bot commented Aug 6, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • track the root conversation selected by each OpenCode TUI instead of inferring selection from server-global events
  • keep attached-client activity and root creation from replacing or suppressing the pane's durable session identity
  • preserve server lifecycle sequencing while allowing TUI-local selection to reanchor restore state
  • install the TUI companion through a comment-preserving tui.jsonc entry without blocking OpenCode's config migration

Validation

  • just check
  • live disposable-session coverage with OpenCode 1.17.8 and 1.18.15
  • verified route-only session selection, attached-client activity and root creation isolation, subsequent selection, and restart restore

refs #2450

@coderabbitai

coderabbitai Bot commented Aug 6, 2026

Copy link
Copy Markdown

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 243242c4-3a05-4ef0-8861-1c63223c04e2

📥 Commits

Reviewing files that changed from the base of the PR and between c62f51c and b9ad03a.

📒 Files selected for processing (2)
  • docs/next/CHANGELOG.md
  • justfile
🚧 Files skipped from review as they are similar to previous changes (2)
  • justfile
  • docs/next/CHANGELOG.md

📝 Walkthrough

Walkthrough

OpenCode now tracks the TUI-selected root session through a dedicated plugin. Installation manages the plugin and JSONC configuration. Terminal state distinguishes local selection from server activity and rejects unrelated session reports.

Changes

OpenCode TUI session selection

Layer / File(s) Summary
TUI session reporting
src/integration/assets/opencode/herdr-tui-session.js, src/integration/assets/opencode/herdr-tui-session.test.ts, justfile
The TUI plugin reports selected root sessions, retries during process detection, ignores child sessions, and stops polling on disposal.
Plugin configuration and lifecycle
src/integration/opencode_config.rs, src/integration/targets.rs, src/integration/actions.rs, src/integration/types.rs, src/integration/tests.rs
Installation and uninstallation manage the TUI plugin and tui.jsonc, including validation, JSONC preservation, cleanup errors, and result paths.
Integration status
src/integration/registry.rs, src/cli/integration.rs, src/integration/mod.rs
Status checks the TUI plugin version and configuration. Incomplete current installations report needs repair.
Session ownership and restore lifecycle
src/terminal/state.rs, src/integration/assets/opencode/herdr-agent-state.js, src/integration/assets/opencode/herdr-agent-state.test.ts, src/agent_resume.rs, docs/next/CHANGELOG.md
Local "select" events can establish or reanchor sessions. Server "new" and "resume" activity does not replace local ownership. Reports from mismatched sessions are rejected.

Estimated code review effort: 4 (Complex) | ~45 minutes

Sequence Diagram(s)

sequenceDiagram
  participant OpenCodeTUI
  participant HerdrTUIPlugin
  participant TerminalState
  OpenCodeTUI->>HerdrTUIPlugin: Select root session
  HerdrTUIPlugin->>TerminalState: Report unsequenced "select"
  TerminalState->>TerminalState: Reconcile local session ownership
  OpenCodeTUI->>TerminalState: Send server session activity
  TerminalState-->>OpenCodeTUI: Reject mismatched session report
Loading

Possibly related PRs

  • herdrdev/herdr#2062: Extends the same OpenCode session-ownership and lifecycle tracking logic.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 51.61% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the main change: tracking OpenCode session switches.
Description check ✅ Passed The description directly explains the session-tracking changes, TUI integration, configuration updates, and validation performed.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch akbash/2450-opencode-session-switch

Comment @coderabbitai help to get the list of available commands.

@akbash-bot akbash-bot added the ai-review Trigger automated AI reviews for pull requests admitted by the PR gate label Aug 6, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1


ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 9dc12150-e42a-4e5c-b532-02d4ecce4fe4

📥 Commits

Reviewing files that changed from the base of the PR and between 69a07fd and 43f6e7f.

📒 Files selected for processing (5)
  • docs/next/CHANGELOG.md
  • src/integration/assets/opencode/herdr-agent-state.js
  • src/integration/assets/opencode/herdr-agent-state.test.ts
  • src/integration/mod.rs
  • src/terminal/state.rs

Comment thread src/integration/assets/opencode/herdr-agent-state.js Outdated
@greptile-apps

greptile-apps Bot commented Aug 6, 2026

Copy link
Copy Markdown

Greptile Summary

The PR separates OpenCode’s server-global activity reporting from TUI-local session selection so each pane retains the root conversation selected in its own TUI.

  • Adds and installs a TUI companion plugin through a comment-preserving tui.jsonc entry.
  • Reworks OpenCode lifecycle reconciliation to accept local selection reports while rejecting attached-client cross-talk.
  • Extends integration status, repair, uninstall, and automated coverage for both OpenCode plugins.

Confidence Score: 5/5

The PR appears safe to merge.

No blocking failure remains.

Important Files Changed

Filename Overview
src/integration/assets/opencode/herdr-tui-session.js Adds polling and bounded retry logic that reports the root session selected by the local OpenCode TUI.
src/terminal/state.rs Adds OpenCode-specific selection reconciliation and cross-talk suppression while retaining lifecycle sequencing.
src/integration/opencode_config.rs Adds comment-preserving, idempotent management of the companion plugin entry in OpenCode’s TUI configuration.
src/integration/targets.rs Installs, validates, and removes both OpenCode integration assets and their managed configuration.
src/integration/registry.rs Marks an otherwise current OpenCode integration as needing repair when its TUI asset or configuration entry is missing.

Sequence Diagram

sequenceDiagram
    participant TUI as OpenCode TUI
    participant Companion as TUI companion plugin
    participant Herdr as Herdr pane API
    participant State as TerminalState
    participant ServerPlugin as OpenCode server plugin

    TUI->>Companion: Select root conversation
    Companion->>Herdr: "report_agent_session(source=select)"
    Herdr->>State: Reanchor durable session identity
    ServerPlugin->>Herdr: Report server-global activity
    Herdr->>State: Route lifecycle update
    State->>State: Ignore activity for another root
    State-->>Herdr: Preserve TUI-selected session
Loading

Reviews (5): Last reviewed commit: "Merge branch 'master' into akbash/2450-o..." | Re-trigger Greptile

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1


ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: c7ae0178-b40a-47ec-ba71-8dd4d1caf285

📥 Commits

Reviewing files that changed from the base of the PR and between 43f6e7f and 782e2f6.

📒 Files selected for processing (2)
  • src/integration/assets/opencode/herdr-agent-state.js
  • src/integration/assets/opencode/herdr-agent-state.test.ts
🚧 Files skipped from review as they are similar to previous changes (1)
  • src/integration/assets/opencode/herdr-agent-state.js

Comment thread src/integration/assets/opencode/herdr-agent-state.test.ts Outdated
@ogulcancelik
ogulcancelik force-pushed the akbash/2450-opencode-session-switch branch from bbcbfc7 to c62f51c Compare August 9, 2026 01:58

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (3)
src/integration/assets/opencode/herdr-tui-session.test.ts (1)

112-125: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Consider covering the exhausted-retry branch.

SELECTION_RETRY_DELAYS_MS has three entries. After the last retry, herdr-tui-session.js sets nextReportAt to Number.POSITIVE_INFINITY and stops reporting the same selection. No test asserts that the reporting stops. A test that waits past the final delay and asserts a stable request count would lock in that boundary.

src/terminal/state.rs (2)

1374-1375: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Consider recording the stale session when a selection clears suppression.

selection_can_reconcile removes the suppression entry for the source without inspecting suppressed.reason. Every other removal site distinguishes HookClear from ProcessExit. clear_full_lifecycle_hook_suppression_for_detected_agent records the suppressed session_ref as a stale session before it drops a HookClear entry (lines 1098-1106). This path drops it silently, so a later report that carries the previous session ref is not filtered by full_lifecycle_hook_report_matches_stale_session.

The opencode_cross_talk guard at lines 863-870 rejects that report while the process is present and the anchor differs, so the reachable exposure is small. Recording the stale session here would keep the two paths consistent.

♻️ Suggested change
         if selection_can_reconcile {
-            self.suppressed_full_lifecycle_hook_reports.remove(&source);
+            if let Some(suppressed) = self.suppressed_full_lifecycle_hook_reports.remove(&source) {
+                if let Some(suppressed_ref) = suppressed
+                    .session_ref
+                    .filter(|suppressed_ref| suppressed_ref != &session_ref)
+                {
+                    self.remember_stale_full_lifecycle_hook_session(
+                        source.clone(),
+                        suppressed.agent_label,
+                        suppressed_ref,
+                    );
+                }
+            }
         } else if full_lifecycle_source && unsequenced_selection {

4620-4656: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Consider adding a boundary test for cross-talk while the process is absent.

opencode_cross_talk at lines 863-870 requires process_present. When the process is absent, a report carrying a different session ref still reaches the buffering path at lines 906-953. That asymmetry is intentional, but no test pins it. A test that clears the detected agent and then sends a mismatched sequenced report would document the boundary.


ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: aec6c888-df3f-48b4-b55f-1b0f88080b93

📥 Commits

Reviewing files that changed from the base of the PR and between 782e2f6 and c62f51c.

📒 Files selected for processing (16)
  • docs/next/CHANGELOG.md
  • justfile
  • src/agent_resume.rs
  • src/cli/integration.rs
  • src/integration/actions.rs
  • src/integration/assets/opencode/herdr-agent-state.js
  • src/integration/assets/opencode/herdr-agent-state.test.ts
  • src/integration/assets/opencode/herdr-tui-session.js
  • src/integration/assets/opencode/herdr-tui-session.test.ts
  • src/integration/mod.rs
  • src/integration/opencode_config.rs
  • src/integration/registry.rs
  • src/integration/targets.rs
  • src/integration/tests.rs
  • src/integration/types.rs
  • src/terminal/state.rs
🚧 Files skipped from review as they are similar to previous changes (2)
  • docs/next/CHANGELOG.md
  • src/integration/assets/opencode/herdr-agent-state.js

Comment thread src/integration/tests.rs
Comment thread src/terminal/state.rs
@ogulcancelik
ogulcancelik merged commit ccccda5 into master Aug 10, 2026
7 checks passed
@kangal-bot kangal-bot removed the ai-review Trigger automated AI reviews for pull requests admitted by the PR gate label Aug 10, 2026
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.

3 participants