Skip to content

feat: add cursor agent cli integration for session restore#506

Merged
ogulcancelik merged 6 commits into
ogulcancelik:masterfrom
udirom:feat/cursor-agent-integration
Jun 8, 2026
Merged

feat: add cursor agent cli integration for session restore#506
ogulcancelik merged 6 commits into
ogulcancelik:masterfrom
udirom:feat/cursor-agent-integration

Conversation

@udirom

@udirom udirom commented Jun 7, 2026

Copy link
Copy Markdown
Contributor

Summary

Adds Cursor Agent CLI integration so herdr can track and restore Cursor agent sessions from tmux panes.

  • herdr integration install cursor / uninstall cursor
  • Installs ~/.cursor/herdr-agent-state.sh and registers a sessionStart hook in ~/.cursor/hooks.json
  • Reports session_id / conversation_id via pane report-agent-session
  • Resume via agent --resume <id>; screen-detected state (session-only pattern, aligned with Codex/Droid)

Discussion: #505

Test plan

  • cargo test integration:: (install/uninstall/idempotency tests added)
  • herdr integration install cursor on a machine with ~/.cursor/hooks.json
  • Start a Cursor agent session in a herdr-managed pane; verify session is reported
  • Restore pane and confirm agent --resume is suggested/applied

Note: Full just ci not run locally (Zig required for libghostty-vt vendored build).

Contributor note

First-time contributor (udirom) — per CONTRIBUTING, maintainer /approve may be required before merge. Happy to address review feedback.

Made with Cursor

@kangal-bot

Copy link
Copy Markdown
Collaborator

Hi @udirom, thanks for your interest in contributing!

New contributors need maintainer approval before opening PRs. This keeps review time focused on accepted work and avoids wasted effort.

Herdr is opinionated about how it should look, feel, and work. Feature requests, ideas, questions, contribution proposals, and product-direction checks belong in Discussions, not issues.

Next steps:

  1. If this is a feature or behavior change, open a Discussion describing what you want to change and why
  2. If the work is accepted, a maintainer may convert the discussion into an issue or create a new issue for it
  3. If this is a reproducible bug, open a bug report using the issue template
  4. Wait for maintainer approval on an accepted issue before opening a PR
    Maintainers approve first-time PR paths with /approve @your-github-username on the accepted issue.
  5. Keep it concise and write in your own voice

A discussion, issue, branch, or proposed implementation does not reserve the work and does not mean the PR path is approved.

This PR will be closed automatically. See https://github.com/ogulcancelik/herdr/blob/master/CONTRIBUTING.md for more details.

@kangal-bot kangal-bot closed this Jun 7, 2026
@udirom

udirom commented Jun 7, 2026

Copy link
Copy Markdown
Contributor Author

Hi @ogulcancelik — first-time contributor here, pinging for review when you have a moment.

I opened Discussion #505 first to propose the Cursor Agent CLI integration (session-only pattern, aligned with Codex/Droid). This PR implements that proposal:

  • herdr integration install cursor / uninstall cursor
  • sessionStart hook → pane report-agent-session
  • Resume via agent --resume <id>, screen-detected state

I understand the approval gate for new contributors — if this looks good in principle, could you /approve @udirom on an issue (or convert the discussion) so the PR path is unblocked?

Happy to iterate on hook install path, docs, or anything else. Thanks for herdr!

@ogulcancelik ogulcancelik reopened this Jun 7, 2026
@ogulcancelik

Copy link
Copy Markdown
Owner

@udirom this looks directionally good. a few changes before merge:

  • use cursor-agent as the cli command herdr launches for restore, not agent. agent is too generic and can collide with other tools like grok. restore should be cursor-agent --resume <id>.
  • do not launch plain agent from herdr. if cursor-agent is missing, the integration should be unavailable or fail clearly.
  • update availability detection and docs to use cursor-agent.
  • keep it session-only. cursor state should continue to come from screen detection, which this pr already does.
  • please confirm one manual end-to-end test: install hook, start cursor agent in a herdr pane, verify session id is reported, restart/restore, and confirm herdr resumes with cursor-agent --resume <id>.

@udirom

udirom commented Jun 7, 2026

Copy link
Copy Markdown
Contributor Author

Thanks for the review — addressed in 9a04363:

  • Restore command is now cursor-agent --resume <id> (not agent).
  • Install fails clearly if cursor-agent is not on PATH (before touching hooks).
  • Availability uses cursor-agent only — no generic agent binary.
  • Docs updated (integrations.mdx, session-state.mdx).
  • Session-only unchanged — hook still only calls pane.report_agent_session; state stays screen-detected.

Manual E2E (partial — local herdr is 0.6.4)

Full loop needs herdr built from this branch: my running server (0.6.4) doesn't expose pane.report_agent_session yet, so the hook can't report session ids against the installed binary.

What I verified locally:

  • cursor-agent on PATH (~/.local/bin/cursor-agent)
  • cursor-agent --help shows --resume [chatId]
  • Hook script sends pane.report_agent_session with source=herdr:cursor, agent=cursor, and session_id/conversation_id from sessionStart JSON
  • Unit test covers resume argv: ["cursor-agent", "--resume", "<id>"]

Happy to re-run the full install → session report → restart → restore loop once this is merged or if you have a preferred way to test against a branch build without Zig/libghostty-vt locally.

@udirom

udirom commented Jun 7, 2026

Copy link
Copy Markdown
Contributor Author

@ogulcancelik — follow-up on the manual E2E ask.

Built this branch locally (herdr 0.6.8) and ran through it:

  • integration install cursor — hook + hooks.json updated; fails cleanly if cursor-agent isn’t on PATH
  • Started cursor-agent -p --trust in a herdr pane — detected as cursor, session reported with source=herdr:cursor
  • Confirmed session.json persists the session id
  • server stop → restart → restored agent still has the same agent_session
  • Resume argv unit test passes: cursor-agent --resume <id> (not generic agent)

One nuance: cursor-agent -p doesn’t fire sessionStart hooks (tested with a wrapper — no hook input). The real path is interactive cursor-agent in a pane. And the actual --resume spawn happens when the TUI client attaches, not from headless server/CLI alone.

Added scripts/e2e-cursor-integration.sh on the branch for the automated slice of this.

Suggestion — plugin-shaped integrations: each new agent currently needs a core PR (Rust + assets + docs + review cycle). Would you be open to a Discussion on loading integrations from a manifest + hook bundle under the user config dir? Community could ship Cursor-style agents without waiting on first-contributor approval for every tool.

Suggestion — contributor skill: I added .codex/skills/herdr-add-agent-integration/ (checklist + traps from this PR). Happy to move/rename it wherever you prefer if it helps the next integration land faster.

Let me know if you want me to re-run anything interactively before merge.

@udirom

udirom commented Jun 7, 2026

Copy link
Copy Markdown
Contributor Author

Moved the E2E script and contributor skill out of the branch — they were scope creep for this PR.

Copies here (gist, not for merge):

https://gist.github.com/udirom/15f181bc9366c60ab3642aec94b2ffe8

Contains:

  • scripts/e2e-cursor-integration.sh
  • .codex/skills/herdr-add-agent-integration/SKILL.md
  • references/integration-checklist.md

Happy to open a separate PR or Discussion if any of this is worth upstreaming later.

@ogulcancelik

ogulcancelik commented Jun 7, 2026

Copy link
Copy Markdown
Owner

Thanks, the runtime behavior from the earlier review looks mostly addressed: restore now uses cursor-agent --resume <id>, availability/install use only cursor-agent, and Cursor remains session-only.

Please fix these before merge:

  • The branch currently conflicts with upstream (sorry)
  • just test-one cursor fails on PR head. The failing assertion is in src/integration/mod.rs:5254: the test expects herdr-agent-state.sh session, but the installed command is shell-quoted as bash '.../herdr-agent-state.sh' session.
  • The happy-path Cursor install tests depend on a real cursor-agent on the reviewer/CI PATH. Please create a fake executable in a temp bin dir and set PATH in those tests, then keep the missing-binary test as the negative case.
  • docs/next/website/src/content/docs/agents.mdx:42 still omits Cursor from the session-identity integration list.

Suggestion — plugin-shaped integrations: each new agent currently needs a core PR (Rust + assets + docs + review cycle). Would you be open to a Discussion on loading integrations from a manifest + hook bundle under the user config dir? Community could ship Cursor-style agents without waiting on first-contributor approval for every tool.

i'm working on something about this stay tuned :)

@udirom

udirom commented Jun 7, 2026

Copy link
Copy Markdown
Contributor Author

Addressed all four review items in c035fa7: merged master, fixed sessionStart hook test for bash-quoted commands, added fake cursor-agent shim for happy-path install tests, and added Cursor to agents.mdx session-identity list.

Locally just test-one cursor passes (55/55). CI shows action_required on my fork PR — could you approve workflow run when you have a moment?

@ogulcancelik

Copy link
Copy Markdown
Owner

@udirom ill take over this pr and merge soon

udirom and others added 6 commits June 8, 2026 03:16
Follow the codex/droid session-only integration pattern: hook script at
~/.cursor/herdr-agent-state.sh, sessionStart entry in hooks.json, and
pane.report_agent_session for native restore via `agent --resume`.
State stays on screen detection (is_reserved_native_state_source).

Co-authored-by: Cursor <cursoragent@cursor.com>
Validate sessionStart in the hook script, avoid treating any generic
`agent` binary as the Cursor CLI for integration availability, prefer
session_id over conversation_id for resume, and document Cursor in
session-state, agents, and cli-reference docs.

Co-authored-by: Cursor <cursoragent@cursor.com>
Address review feedback: resume via `cursor-agent --resume <id>` instead
of generic `agent`, fail install when cursor-agent is missing from PATH,
and update docs accordingly. Session-only + screen-detected state unchanged.

Co-authored-by: Cursor <cursoragent@cursor.com>
Capture manual test automation and contributor workflow from the Cursor
integration work so future agents follow the same install/hook/resume pattern.

Co-authored-by: Cursor <cursoragent@cursor.com>
Keep the PR focused on the cursor integration itself; auxiliary artifacts
live in a PR comment gist instead.

Co-authored-by: Cursor <cursoragent@cursor.com>
@ogulcancelik ogulcancelik force-pushed the feat/cursor-agent-integration branch from fb1834a to 64fb6ac Compare June 8, 2026 00:19
@ogulcancelik ogulcancelik merged commit 5fe527d into ogulcancelik:master Jun 8, 2026
4 checks passed
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