Context
scan_repos() in agent/hub-agent.py lists non-dot directories exactly one level deep under REPOS_ROOT that contain a .git entry. New sessions branch off that checkout's current HEAD. The hub displays each repo's branch and dirty count but offers no repo-level actions — only session-level ones.
Problem
- Stale bases: if nobody pulls the checkout on the host, every new session starts from an old
HEAD and the first thing each agent does is work on stale code (or waste tokens fetching/rebasing). There's no way to freshen a repo from the dashboard.
- Fixed layout: repos nested deeper than one level (e.g.
git/work/foo) or grouped in subdirectories are invisible. The depth is hardcoded.
Proposal
- Repo commands: add repo-scoped commands alongside the session ones —
{type:"repo-fetch", repo} and {type:"repo-pull", repo} (git pull --ff-only to guarantee it never creates merge states on the shared checkout; refuse with a reported error if not fast-forwardable or dirty). Queued and acked exactly like session commands. UI: a small ↻ action in the repo header row, showing ahead/behind against origin (one git rev-list --count pair per repo per beat, matching what's proposed per-session in the unpushed-work issue).
- Scan depth:
REPOS_SCAN_DEPTH env (default 1, as today) with scan_repos() walking up to that depth, skipping dot-dirs at each level (.agenthub stays excluded by the existing dot-dir rule). Repo name becomes the relative path (work/foo) so names stay unique; slugify() already makes that safe for rcName use.
- Clone (stretch): a
{type:"repo-clone", url} command would let a brand-new repo be added to a host from the hub. Bigger security surface (arbitrary URL → command line), so keep it a separate decision; listing it here for completeness.
Touchpoints
agent/hub-agent.py — scan_repos(), repo_entry() ahead/behind, new commands
agent-hub/server.js — endpoints
agent-hub/public/index.html — repo header actions + freshness display
Context
scan_repos()inagent/hub-agent.pylists non-dot directories exactly one level deep underREPOS_ROOTthat contain a.gitentry. New sessions branch off that checkout's currentHEAD. The hub displays each repo's branch and dirty count but offers no repo-level actions — only session-level ones.Problem
HEADand the first thing each agent does is work on stale code (or waste tokens fetching/rebasing). There's no way to freshen a repo from the dashboard.git/work/foo) or grouped in subdirectories are invisible. The depth is hardcoded.Proposal
{type:"repo-fetch", repo}and{type:"repo-pull", repo}(git pull --ff-onlyto guarantee it never creates merge states on the shared checkout; refuse with a reported error if not fast-forwardable or dirty). Queued and acked exactly like session commands. UI: a small ↻ action in the repo header row, showing ahead/behind againstorigin(onegit rev-list --countpair per repo per beat, matching what's proposed per-session in the unpushed-work issue).REPOS_SCAN_DEPTHenv (default 1, as today) withscan_repos()walking up to that depth, skipping dot-dirs at each level (.agenthubstays excluded by the existing dot-dir rule). Reponamebecomes the relative path (work/foo) so names stay unique;slugify()already makes that safe for rcName use.{type:"repo-clone", url}command would let a brand-new repo be added to a host from the hub. Bigger security surface (arbitrary URL → command line), so keep it a separate decision; listing it here for completeness.Touchpoints
agent/hub-agent.py—scan_repos(),repo_entry()ahead/behind, new commandsagent-hub/server.js— endpointsagent-hub/public/index.html— repo header actions + freshness display