feat(probe): import the desktop probe core into crates/probe (phase 1)

Merged
KH
7d ago
+321684-0

Summary

Phase 1 of moving the Agent Relay desktop probe core into relay. The probe is the native Rust daemon that discovers running agent sessions (Claude Code, Codex, Devin, OpenCode, Grok, Pi, …) and injects Relay messages into them through each harness's native route. With it in relay, the CLI (relay init) can install and run it headless, without the desktop GUI. relay 15.0.0 is held until injection works through the probe.

  • Clean snapshot of relay-desktop origin/main (5601b739) probe/ → crates/probe/. No relay-desktop history comes along: that history has scrubbed internal docs and an old PostHog key.
  • Separate Cargo workspace with its own Cargo.lock. It does not join the root workspace yet, because relaycast 10 vs 9, nix =0.25.1 vs 0.30 and portable-pty =0.8.1 vs 0.8 conflict with the broker. Root cargo commands and the broker CI don't see it.
  • Only the core moves. The macOS, GTK (Linux and Windows) and iPad apps stay in relay-desktop. This PR changes nothing in relay-desktop; docs/probe-move.md lists what it must change to consume the core.

What was excluded, and the GTK split

Excluded (stays in relay-desktop):

  • src/linux_app/: the GTK app, about 41k lines.
  • The gtk feature.
  • The agent-relay (GUI launcher) and agent-relay-fake-core binaries.
  • The tests linux_app_gtk (and its directory), linux_app_hosting, linux_app_core_e2e and linux_package.
  • resources/linux and resources/windows.
  • The GUI-only dependencies gtk4, ksni, tray-icon, tauri-winrt-notification, zip and tar. Removing them pruned 107 packages from Cargo.lock, and nothing was added or upgraded.

Only three places in the core used linux_app, and none of them needed GTK:

Core fileUsedResolution
relay/login_item.rslinux_app::install (packaged-app paths; Windows registry helpers)Moved to crate::install
relay/session_query.rsLocalSessionQuery, LocalSessionRow, StatusView, SessionUploadStateMoved the six modules in their closure to crate::session_model
relay/uploader/query.rsStatusViewSame as above

The six modules in crate::session_model are agent_kind, agent_names, local_sessions, session_project, session_query and uploads. They are unchanged apart from paths, and their unit tests came with them. The shared/session-*.json vectors are now in tests/fixtures/shared/.

No core test depended on GTK. The tests left out all test the app; linux_app_core_e2e drives a real core, but through the app's bridge client.

Other changes

  • Version stamping. build.rs no longer reads relay-desktop's CHANGELOG.md.

    • AGENT_RELAY_PROBE_VERSION is stamped exactly, as release builds already pass it.
    • Development builds are <base>-dev+<rev>. The base is AGENT_RELAY_PROBE_BASE_VERSION, which relay-desktop sets to its CalVer, or else the crate version.
  • Contract. relay-contract-codegen defaults to the checked-in crates/probe/contract/CoreContract.swift. It also takes --out FILE and --app-root DIR; the second writes relay-desktop's macOS path. The generated output is byte-identical to relay-desktop's current CoreContract.swift except the two header lines that name the regenerate script and source path.

  • Docs.

    • crates/probe/docs/relay-core.md (the contract test checks its tables) and crates/probe/docs/agent-relay-probe.md were imported.
    • Links to relay-desktop docs that were not imported are now plain-text references.
    • crates/probe/README.md is new, and so is the design note docs/probe-move.md (what moved, what stayed, the GTK split, phases 2–5, and the relay-desktop changes).
  • Open-source hygiene.

    • crates/probe/LICENSE (Apache-2.0, the same as relay); the crate already declares license = "Apache-2.0".
    • crates/probe/scripts/check-open-source.sh ports relay-desktop's check and adds credential patterns. It also flags Relaycast rk_/at_/nt_ values that are not obvious fixtures, and prints only file:line.
    • Neutralised fixture strings: github.com/AgentWorkforce/relay-desktop remote URLs (relay-desktop is private) became acme/..., and personal handles became ada-lovelace/sam-codex.
    • GitHub push protection read four long rk_live_/rk_test_ fixtures in workspace_recovery_tests.rs (repeated or sequential characters, not real keys) as Stripe restricted keys. They are now built with concat! instead of being allowlisted.
  • CI. .github/workflows/probe-ci.yml runs only for changes under crates/probe/** (and its own file). It runs:

    • Linux x64 build and test, with an empty HOME;
    • macOS arm64 build and test;
    • Windows x64 build (MSVC);
    • the contract-drift check;
    • the public-source check.

    Actions are pinned to the SHAs relay already uses. PR runs cancel superseded runs, and other runs get a per-SHA group (the #2010 pattern).

No CHANGELOG entry: this is internal and not user-visible yet.

Test plan

  • cargo build --locked (Linux x64).
  • cargo test --locked (Linux x64, empty HOME, clean env): about 3,380 passed and 19 ignored. One timing test, live::selected_remote::tests::selected_claude_worker_refreshes_shallow_catalog_and_selected_evidence (an 8 s eventually deadline in code this PR does not touch), is flaky: it failed in 1 of 2 runs of the binary's tests and passes on its own. cloud::tests::cloud_bearer_reuses_only_a_matching_unexpired_official_cli_session fails only when the caller's environment has Agent Relay or Claude variables set, and passes under env -i with a temp HOME. A live_capture stop-timing test failed once under a loaded first run and passed on the clean rerun.
  • scripts/generate-contract.sh regenerates contract/CoreContract.swift with no diff.
  • scripts/check-open-source.sh passes, and a staged canary key, private link and home path were all flagged.
  • probe-ci on macOS arm64 and Windows x64 (first runs on this PR).

Blockers and notes for phase 2

  • src/relay/workspace.rs resolves the Relaycast workspace only from the Cloud sign-in. Phase 2 must follow the CLI ladder: env key → project workspace-key.json → ~/.agentworkforce/relay/workspaces.json, plus the relaycast-origins.json origin bindings. The core already locates the CLI home (workspace::relay_home) but only reads it.
  • Not ported from relay-desktop CI yet: rust-oleum (the config is pruned of GUI entries), the glibc floor, and the arm64 Linux, x64 macOS and arm64 Windows lanes.
  • rustfmt --check reports drift in about 80 upstream files. They were left verbatim to keep the snapshot faithful, so CI does not gate on fmt.

🤖 Generated with Claude Code


View with [code]smith Autofix with [code]smith
Need help on this PR? Tag @codesmith-bot with what you need.


Agent Relay sessions

  • claude session aabfa8cf · opened via gh pr create · last active 2026-10-29
  • claude session 5a4f854b · contributor · ran gh pr commands · last active 2026-10-29