agent-control-plane 0.2.0 → 0.4.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (59) hide show
  1. package/README.md +69 -19
  2. package/assets/workflow-catalog.json +1 -1
  3. package/bin/pr-risk.sh +22 -7
  4. package/bin/sync-pr-labels.sh +1 -1
  5. package/hooks/heartbeat-hooks.sh +125 -12
  6. package/hooks/issue-reconcile-hooks.sh +1 -1
  7. package/hooks/pr-reconcile-hooks.sh +1 -1
  8. package/npm/bin/agent-control-plane.js +296 -61
  9. package/package.json +11 -7
  10. package/tools/bin/agent-github-update-labels +36 -2
  11. package/tools/bin/agent-project-catch-up-merged-prs +4 -2
  12. package/tools/bin/agent-project-cleanup-session +49 -5
  13. package/tools/bin/agent-project-heartbeat-loop +119 -1471
  14. package/tools/bin/agent-project-publish-issue-pr +6 -3
  15. package/tools/bin/agent-project-reconcile-issue-session +78 -106
  16. package/tools/bin/agent-project-reconcile-pr-session +166 -143
  17. package/tools/bin/agent-project-retry-state +18 -7
  18. package/tools/bin/agent-project-run-claude-session +10 -0
  19. package/tools/bin/agent-project-run-codex-resilient +99 -14
  20. package/tools/bin/agent-project-run-codex-session +16 -5
  21. package/tools/bin/agent-project-run-kilo-session +10 -0
  22. package/tools/bin/agent-project-run-openclaw-session +10 -0
  23. package/tools/bin/agent-project-run-opencode-session +10 -0
  24. package/tools/bin/agent-project-sync-source-repo-main +163 -0
  25. package/tools/bin/agent-project-worker-status +10 -7
  26. package/tools/bin/cleanup-worktree.sh +6 -1
  27. package/tools/bin/flow-config-lib.sh +1257 -34
  28. package/tools/bin/flow-resident-worker-lib.sh +119 -1
  29. package/tools/bin/flow-shell-lib.sh +56 -0
  30. package/tools/bin/github-core-rate-limit-state.sh +77 -0
  31. package/tools/bin/github-write-outbox.sh +470 -0
  32. package/tools/bin/heartbeat-loop-cache-lib.sh +164 -0
  33. package/tools/bin/heartbeat-loop-counting-lib.sh +306 -0
  34. package/tools/bin/heartbeat-loop-pr-strategy-lib.sh +199 -0
  35. package/tools/bin/heartbeat-loop-scheduling-lib.sh +506 -0
  36. package/tools/bin/heartbeat-loop-worker-lib.sh +319 -0
  37. package/tools/bin/heartbeat-recovery-preflight.sh +12 -1
  38. package/tools/bin/heartbeat-safe-auto.sh +56 -3
  39. package/tools/bin/install-project-launchd.sh +17 -2
  40. package/tools/bin/project-init.sh +21 -1
  41. package/tools/bin/project-launchd-bootstrap.sh +16 -9
  42. package/tools/bin/project-runtimectl.sh +46 -2
  43. package/tools/bin/reconcile-bootstrap-lib.sh +113 -0
  44. package/tools/bin/resident-issue-controller-lib.sh +448 -0
  45. package/tools/bin/scaffold-profile.sh +61 -3
  46. package/tools/bin/start-pr-fix-worker.sh +47 -10
  47. package/tools/bin/start-resident-issue-loop.sh +28 -439
  48. package/tools/dashboard/app.js +37 -1
  49. package/tools/dashboard/dashboard_snapshot.py +65 -26
  50. package/tools/templates/pr-fix-template.md +3 -1
  51. package/tools/templates/pr-merge-repair-template.md +2 -1
  52. package/SKILL.md +0 -149
  53. package/references/architecture.md +0 -217
  54. package/references/commands.md +0 -128
  55. package/references/control-plane-map.md +0 -124
  56. package/references/docs-map.md +0 -73
  57. package/references/release-checklist.md +0 -65
  58. package/references/repo-map.md +0 -36
  59. package/tools/bin/split-retained-slice.sh +0 -124
@@ -1,128 +0,0 @@
1
- # Command Map
2
-
3
- Run commands from the current isolated checkout for the task.
4
-
5
- Profile-specific repo roots and repo-local dev/test commands belong in
6
- `~/.agent-runtime/control-plane/profiles/<id>/README.md`. Resolve the active
7
- profile first, then use the selected profile's notes for product-repo commands.
8
-
9
- ## Profile Resolution
10
-
11
- ```bash
12
- bash tools/bin/workflow-catalog.sh profiles
13
- tools/bin/workflow-catalog.sh context
14
- bash tools/bin/profile-activate.sh --profile-id <id>
15
- ACP_PROJECT_ID=<id> bash tools/bin/render-flow-config.sh
16
- ```
17
-
18
- Use `render-flow-config.sh` when you need the effective repo root, worktree
19
- root, runtime root, worker backend, or profile-specific script bindings.
20
- When multiple available profiles exist, set `ACP_PROJECT_ID=<id>` first or use
21
- `profile-activate.sh --profile-id <id>` before running manual operator
22
- commands.
23
-
24
- ## Dependency bootstrap
25
-
26
- Run dependency bootstrap only from the clean automation baseline for the
27
- selected profile when you explicitly need to refresh shared dependencies. Do not
28
- repair shared `node_modules` from inside a worker worktree.
29
-
30
- For control-plane changes in this repo, prefer focused shell tests over broad
31
- bootstrap unless the task actually changes dependency behavior.
32
-
33
- ## Control-Plane Verification
34
-
35
- ```bash
36
- bash tools/bin/check-skill-contracts.sh
37
- bash tools/bin/flow-runtime-doctor.sh
38
- bash tools/bin/profile-smoke.sh
39
- bash tools/bin/test-smoke.sh
40
- bash tools/tests/test-project-init.sh
41
- bash tools/tests/test-project-init-force-and-skip-sync.sh
42
- bash tools/tests/test-project-remove.sh
43
- bash tools/tests/test-project-runtimectl.sh
44
- bash tools/tests/test-project-runtimectl-missing-profile.sh
45
- bash tools/tests/test-project-runtimectl-stop-cancels-pending-kick.sh
46
- bash tools/tests/test-project-runtimectl-start-falls-back-to-bootstrap.sh
47
- bash tools/tests/test-project-runtimectl-status-supervisor-running.sh
48
- bash tools/tests/test-project-launchd-bootstrap.sh
49
- bash tools/tests/test-install-project-launchd.sh
50
- bash tools/tests/test-uninstall-project-launchd.sh
51
- bash tools/tests/test-project-runtimectl-launchd.sh
52
- bash tools/tests/test-dashboard-launchd-bootstrap.sh
53
- bash tools/tests/test-install-dashboard-launchd.sh
54
- bash tools/tests/test-render-dashboard-snapshot.sh
55
- bash tools/tests/test-serve-dashboard.sh
56
- bash tools/tests/test-control-plane-dashboard-runtime-smoke.sh
57
- bash tools/tests/test-workflow-catalog.sh
58
- bash tools/tests/test-render-flow-config.sh
59
- ```
60
-
61
- Add or run targeted tests in `tools/tests/` for the changed surface.
62
-
63
- ## Flow maintenance
64
-
65
- ```bash
66
- tools/bin/flow-runtime-doctor.sh
67
- tools/bin/workflow-catalog.sh list
68
- tools/bin/workflow-catalog.sh show pr-review
69
- tools/bin/workflow-catalog.sh profiles
70
- tools/bin/workflow-catalog.sh context
71
- tools/bin/profile-activate.sh --profile-id <id>
72
- tools/bin/project-init.sh --profile-id <id> --repo-slug <owner/repo>
73
- tools/bin/render-flow-config.sh
74
- tools/bin/scaffold-profile.sh --profile-id <id> --repo-slug <owner/repo>
75
- tools/bin/profile-smoke.sh
76
- tools/bin/test-smoke.sh
77
- tools/bin/profile-adopt.sh --profile-id <id>
78
- tools/bin/project-runtimectl.sh status --profile-id <id>
79
- tools/bin/project-runtimectl.sh sync --profile-id <id>
80
- tools/bin/project-runtimectl.sh stop --profile-id <id>
81
- tools/bin/project-runtimectl.sh start --profile-id <id>
82
- tools/bin/project-runtimectl.sh restart --profile-id <id>
83
- tools/bin/install-project-launchd.sh --profile-id <id>
84
- tools/bin/uninstall-project-launchd.sh --profile-id <id>
85
- tools/bin/project-remove.sh --profile-id <id>
86
- tools/bin/project-remove.sh --profile-id <id> --purge-paths
87
- tools/bin/sync-shared-agent-home.sh
88
- python3 tools/dashboard/dashboard_snapshot.py --pretty
89
- bash tools/bin/serve-dashboard.sh --host 127.0.0.1 --port 8765
90
- bash tools/bin/install-dashboard-launchd.sh --host 127.0.0.1 --port 8765
91
- ```
92
-
93
- Installed profile prompts should live under
94
- `~/.agent-runtime/control-plane/profiles/<id>/templates/`; generic fallback
95
- prompts live under `tools/templates/`.
96
-
97
- ## Dashboard
98
-
99
- ```bash
100
- python3 tools/dashboard/dashboard_snapshot.py --pretty
101
- bash tools/bin/serve-dashboard.sh --host 127.0.0.1 --port 8765
102
- bash tools/bin/install-dashboard-launchd.sh --host 127.0.0.1 --port 8765
103
- ```
104
-
105
- Use the snapshot command for CLI/debug output and the HTTP server for the live
106
- dashboard at `http://127.0.0.1:8765`. Use the LaunchAgent installer when you
107
- want the dashboard to come back automatically after macOS restart/login.
108
-
109
- ## Project Autostart
110
-
111
- ```bash
112
- bash tools/bin/install-project-launchd.sh --profile-id <id>
113
- bash tools/bin/uninstall-project-launchd.sh --profile-id <id>
114
- ```
115
-
116
- Use the project installer when one profile should come back automatically after
117
- macOS restart/login. `project-runtimectl.sh start|stop|status` will detect that
118
- per-project LaunchAgent automatically once it is installed.
119
-
120
- ## Repo-Specific Commands
121
-
122
- After choosing a profile, read `~/.agent-runtime/control-plane/profiles/<id>/README.md` for:
123
-
124
- - clean automation baseline and retained checkout roots
125
- - repo-local startup docs such as `AGENTS.md` and OpenSpec paths
126
- - app/package-specific dev commands
127
- - isolated smoke and release-rehearsal commands
128
- - project-specific operator runbooks
@@ -1,124 +0,0 @@
1
- # Agent Control Plane Map
2
-
3
- This repository is the shared `agent-control-plane` package. It provides a
4
- generic engine that can host multiple installed profiles, each with its own repo
5
- roots, labels, worker preferences, prompts, and project-specific guardrails.
6
-
7
- ## What Lives Here
8
-
9
- - `SKILL.md`
10
- Canonical operating manual for the shared control plane.
11
- - `~/.agent-runtime/control-plane/profiles/<id>/control-plane.yaml`
12
- Canonical installed project profile for repo paths, queue labels, limits,
13
- and script bindings.
14
- - `~/.agent-runtime/control-plane/profiles/<id>/README.md`
15
- Repo-specific operator notes, startup docs, and command references for the
16
- selected profile.
17
- - `~/.agent-runtime/control-plane/profiles/<id>/templates/`
18
- Optional installed profile-specific prompt overrides.
19
- - `assets/workflow-catalog.json`
20
- Declarative catalog of the workflow lanes this control plane exposes.
21
- - `bin/`
22
- Queue, label, and risk logic shared by installed profiles.
23
- - `hooks/`
24
- Heartbeat and reconcile hooks shared by installed profiles.
25
- - `tools/bin/flow-runtime-doctor.sh`
26
- Reports whether the published source copy and runtime-home copy are in sync.
27
- - `tools/bin/workflow-catalog.sh`
28
- Lists workflows, shows workflow details, or prints available profile ids.
29
- - `tools/bin/render-flow-config.sh`
30
- Prints the effective operator/runtime config after environment overrides.
31
- - `tools/bin/run-codex-task.sh`
32
- Routes the shared worker contract into the backend-specific session wrapper.
33
- - `tools/bin/agent-project-run-codex-session`
34
- Launches Codex-backed worker sessions.
35
- - `tools/bin/agent-project-run-claude-session`
36
- Launches Claude-backed worker sessions.
37
- - `tools/bin/agent-project-run-openclaw-session`
38
- Launches OpenClaw-backed worker sessions.
39
- - `tools/bin/agent-project-run-ollama-session`
40
- Launches Ollama-backed worker sessions with a Node.js agentic loop.
41
- - `tools/bin/agent-project-run-pi-session`
42
- Launches Pi-backed worker sessions in `--print --no-session` mode.
43
- - `tools/bin/agent-project-run-opencode-session`
44
- Launches Crush (formerly OpenCode) worker sessions via `crush run`.
45
- - `tools/bin/agent-project-run-kilo-session`
46
- Launches Kilo Code worker sessions via `kilo run --auto --format json`.
47
- - `tools/bin/project-init.sh`
48
- Runs scaffold + smoke + adopt + runtime sync for one installed profile.
49
- - `tools/bin/scaffold-profile.sh`
50
- Scaffolds a new installed profile, profile notes, and prompt templates in the
51
- local profile registry.
52
- - `tools/bin/project-runtimectl.sh`
53
- Provides `status`, `start`, `stop`, and `restart` for one installed profile.
54
- - `tools/bin/project-launchd-bootstrap.sh`
55
- Syncs the runtime copy and runs one profile-scoped heartbeat pass in a
56
- launchd-safe foreground process for the runtime supervisor.
57
- - `tools/bin/install-project-launchd.sh`
58
- Installs a per-user LaunchAgent for one installed profile so its runtime can
59
- come back automatically after reboot/login.
60
- - `tools/bin/uninstall-project-launchd.sh`
61
- Removes the per-project LaunchAgent wrapper and plist for one installed
62
- profile.
63
- - `tools/bin/project-remove.sh`
64
- Removes one installed profile plus ACP-owned runtime state, with optional
65
- purge of ACP-managed repo/worktree/workspace paths.
66
- - `tools/bin/profile-smoke.sh`
67
- Validates available profiles and catches session/branch prefix collisions
68
- before scheduler use.
69
- - `tools/bin/test-smoke.sh`
70
- Runs the main shared-package smoke gates in one operator-facing command.
71
- - `tools/dashboard/dashboard_snapshot.py`
72
- Emits a JSON snapshot of active runs, resident controllers, cooldown state,
73
- queue depth, and scheduled issues across installed profiles.
74
- - `tools/bin/serve-dashboard.sh`
75
- Serves the live worker dashboard and `/api/snapshot.json` endpoint for local
76
- browser-based monitoring.
77
- - `tools/bin/dashboard-launchd-bootstrap.sh`
78
- Syncs the runtime copy and launches the dashboard server in a launchd-safe
79
- foreground process.
80
- - `tools/bin/install-dashboard-launchd.sh`
81
- Installs and bootstraps a per-user LaunchAgent so the dashboard returns after
82
- reboot/login.
83
- - `tools/bin/profile-adopt.sh`
84
- Creates runtime roots, installs the selected profile into the local profile
85
- registry when needed, and syncs the anchor repo plus VS Code workspace for
86
- live scheduler adoption.
87
- - `references/`
88
- Control-plane docs, operator commands, and repository maps.
89
-
90
- ## What Does Not Live Here
91
-
92
- - Repo-specific product code.
93
- - Local scheduler bootstrap and operator docs that belong to a particular
94
- workstation. Those now live under:
95
- `~/.agent-runtime/control-plane/workspace`
96
-
97
- ## Vendored Runtime
98
-
99
- - Runtime engines are resolved from the current skill root first, then the
100
- shared/runtime canonical copies when present, while active project profiles
101
- are resolved from `~/.agent-runtime/control-plane/profiles/`.
102
- - Project-specific instructions should be loaded from the active profile's
103
- `README.md` and templates instead of being hardcoded into the shared engine.
104
-
105
- ## Published Artifacts
106
-
107
- - Source canonical package copy:
108
- `$SHARED_AGENT_HOME/skills/openclaw/agent-control-plane`
109
- - Runtime canonical package copy:
110
- `~/.agent-runtime/runtime-home/skills/openclaw/agent-control-plane`
111
-
112
- Published artifacts are rebuilt by `tools/bin/sync-shared-agent-home.sh` as
113
- concrete copied files, not symlink aliases. Canonical profile configs now live
114
- outside the repo in `~/.agent-runtime/control-plane/profiles/<id>/control-plane.yaml`.
115
-
116
- ## Operational Rule
117
-
118
- When updating the control plane:
119
-
120
- 1. Change the generic engine in this repo or the selected installed profile in the external registry.
121
- 2. Keep workstation wrappers thin.
122
- 3. Repair shared/runtime published copies with `tools/bin/sync-shared-agent-home.sh`.
123
- 4. Prefer explicit profile docs and copied artifacts over hidden defaults and
124
- symlink aliases.
@@ -1,73 +0,0 @@
1
- # Docs Map
2
-
3
- Canonical documentation sources inside `agent-control-plane`:
4
-
5
- ## Shared Control-Plane Docs
6
-
7
- - `SKILL.md`
8
- Shared operating rules and startup sequence.
9
- - `README.md`
10
- Public-facing install, usage, funding, contributing, and security entrypoint.
11
- - `CHANGELOG.md`
12
- Public release history for the package and repository.
13
- - `ROADMAP.md`
14
- Public product and backend-support roadmap, including current and planned
15
- worker integrations.
16
- - `references/architecture.md`
17
- Architecture walkthrough with system, runtime, worker, and dashboard diagrams.
18
- - `CONTRIBUTING.md`
19
- Contributor workflow, legal model, and maintainer expectations.
20
- - `CLA.md`
21
- Contributor license agreement used for incoming changes.
22
- - `CODE_OF_CONDUCT.md`
23
- Community behavior and moderation expectations.
24
- - `SECURITY.md`
25
- Security reporting path and disclosure expectations.
26
- - `references/control-plane-map.md`
27
- Ownership map for profiles, scripts, publication copies, and operator tools.
28
- - `references/commands.md`
29
- Control-plane operator commands and profile-management entrypoints.
30
- - `references/release-checklist.md`
31
- Maintainer release checklist for public package publishing.
32
- - `.github/release-template.md`
33
- Reusable markdown template for GitHub release notes.
34
- - `.github/workflows/ci.yml`
35
- Public CI workflow used for the README status badge.
36
- - `.github/workflows/publish.yml`
37
- Trusted npm publishing workflow used for tag-driven releases with provenance.
38
- - `references/repo-map.md`
39
- Layout of the control-plane repository itself.
40
-
41
- ## Profile-Scoped Docs
42
-
43
- - `~/.agent-runtime/control-plane/profiles/<id>/README.md`
44
- Canonical repo-specific startup docs, repo roots, command map, and
45
- high-risk notes.
46
- - `~/.agent-runtime/control-plane/profiles/<id>/control-plane.yaml`
47
- Canonical machine-readable installed profile config.
48
- - `~/.agent-runtime/control-plane/profiles/<id>/templates/*.md`
49
- Canonical prompt overrides for issue, PR fix, PR review, or scheduled issue flows.
50
-
51
- ## Runtime and Publication Docs
52
-
53
- - `tools/bin/flow-runtime-doctor.sh`
54
- Sync health for source and runtime copies.
55
- - `tools/bin/profile-smoke.sh`
56
- Installed-profile validation before scheduler use.
57
- - `tools/bin/profile-adopt.sh`
58
- Local workstation adoption helper.
59
- - `tools/bin/sync-shared-agent-home.sh`
60
- Publication repair for shared/runtime copies.
61
- - `tools/bin/render-dashboard-demo-media.sh`
62
- Regenerates the README dashboard screenshot and animated walkthrough from a
63
- real local demo fixture.
64
- - `tools/bin/render-architecture-infographics.sh`
65
- Regenerates the architecture infographic PNGs and PDF deck from the local
66
- HTML source in `tools/architecture/`.
67
-
68
- ## Rule of Thumb
69
-
70
- If a piece of guidance is specific to one repo, keep it in
71
- `~/.agent-runtime/control-plane/profiles/<id>/README.md` or
72
- `~/.agent-runtime/control-plane/profiles/<id>/templates/` instead of the shared
73
- control-plane docs.
@@ -1,65 +0,0 @@
1
- # Release Checklist
2
-
3
- Maintainer checklist for shipping a new public package release of
4
- `agent-control-plane`.
5
-
6
- ## Pre-Release
7
-
8
- - confirm `git status` is clean
9
- - confirm `package.json` version is intentional
10
- - review `CHANGELOG.md` and prepare release notes from
11
- `.github/release-template.md`
12
- - review `README.md`, `SECURITY.md`, `CONTRIBUTING.md`, and `CLA.md` for stale
13
- links or policy text
14
- - if a public GitHub repo now exists, set or verify the `homepage`,
15
- `repository`, and `bugs` URLs in `package.json`
16
- - make sure sponsor links still point to the intended maintainer identity
17
- - confirm the intended license is still `MIT`
18
-
19
- ## Verification
20
-
21
- Run the core checks:
22
-
23
- ```bash
24
- bash tools/tests/test-package-public-metadata.sh
25
- bash tools/tests/test-package-funding-metadata.sh
26
- bash tools/tests/test-contribution-docs.sh
27
- bash tools/tests/test-agent-control-plane-npm-cli.sh
28
- bash tools/bin/test-smoke.sh
29
- npm pack --dry-run
30
- ```
31
-
32
- ## Publish
33
-
34
- Recommended release flow uses npm trusted publishing from GitHub Actions, so you
35
- do not have to enter an OTP during every local publish.
36
-
37
- One-time setup:
38
-
39
- - configure `agent-control-plane` for npm trusted publishing from
40
- `ducminhnguyen0319/agent-control-plane`
41
- - verify the publish workflow file is `.github/workflows/publish.yml`
42
- - keep npm package publishing policy on the stricter setting you want after
43
- trusted publishing is working
44
-
45
- Per-release command flow:
46
-
47
- ```bash
48
- npm version <patch|minor|major>
49
- git push origin main --follow-tags
50
- ```
51
-
52
- Then:
53
-
54
- - watch `.github/workflows/publish.yml` for the npm publish run
55
- - create or update a GitHub release using `.github/release-template.md`
56
- - update `CHANGELOG.md` if the final shipped notes differ from the draft
57
-
58
- ## Post-Release
59
-
60
- - verify `npx agent-control-plane@latest help` works from a clean shell
61
- - verify the npm package shows provenance for the new version
62
- - verify `npm fund` shows the expected sponsor link
63
- - verify the repo README, sponsor button, and package metadata all point to the
64
- same maintainer identity
65
- - announce the release where relevant
@@ -1,36 +0,0 @@
1
- # Repository Map
2
-
3
- This file maps the `agent-control-plane` repository itself.
4
-
5
- ## Core Layout
6
-
7
- - `SKILL.md`
8
- Shared operating manual for the control plane.
9
- - `assets/`
10
- Workflow catalog and static non-profile assets.
11
- - `bin/`
12
- Queue, label, and risk scripts shared by installed profiles.
13
- - `hooks/`
14
- Heartbeat and reconcile hooks shared by installed profiles.
15
- - `tools/bin/`
16
- Runtime wrappers, onboarding helpers, publication utilities, and doctor tools.
17
- - `tools/templates/`
18
- Generic fallback prompts used when a profile does not override a template.
19
- - `tools/tests/`
20
- Shell regression coverage for control-plane behavior.
21
- - `references/`
22
- Control-plane docs, operator commands, and repository maps.
23
-
24
- ## Operator Surfaces
25
-
26
- - `tools/bin/render-flow-config.sh`
27
- Effective config viewer for the selected profile.
28
- - `tools/bin/profile-smoke.sh`
29
- Installed-profile validation and collision detection.
30
- - `tools/bin/profile-adopt.sh`
31
- Local runtime/bootstrap helper for onboarding a profile onto a workstation.
32
- - `tools/bin/sync-shared-agent-home.sh`
33
- Publication repair for shared/runtime copies.
34
-
35
- Installed profiles live outside this repo under
36
- `~/.agent-runtime/control-plane/profiles/<id>/`.
@@ -1,124 +0,0 @@
1
- #!/usr/bin/env bash
2
- set -euo pipefail
3
-
4
- SOURCE_ROOT=""
5
- TARGET_ROOT=""
6
- PATHS_FILE=""
7
- BACKUP_ROOT=""
8
- MOVE_MODE="false"
9
-
10
- usage() {
11
- cat <<'EOF'
12
- Usage:
13
- split-retained-slice.sh --source <path> --target <path> --paths-file <file> [options]
14
-
15
- Copies a curated slice of uncommitted changes from one retained worktree to
16
- another. Optionally removes that slice from the source after verifying the copy.
17
-
18
- Options:
19
- --source <path> Source retained worktree
20
- --target <path> Target retained worktree
21
- --paths-file <file> Newline-delimited relative paths to copy
22
- --backup-root <path> Where to store a safety backup copy (default: mktemp)
23
- --move Remove the copied paths from the source after verify
24
- --help Show this help
25
- EOF
26
- }
27
-
28
- while [[ $# -gt 0 ]]; do
29
- case "$1" in
30
- --source) SOURCE_ROOT="${2:-}"; shift 2 ;;
31
- --target) TARGET_ROOT="${2:-}"; shift 2 ;;
32
- --paths-file) PATHS_FILE="${2:-}"; shift 2 ;;
33
- --backup-root) BACKUP_ROOT="${2:-}"; shift 2 ;;
34
- --move) MOVE_MODE="true"; shift ;;
35
- --help|-h) usage; exit 0 ;;
36
- *) echo "Unknown argument: $1" >&2; usage >&2; exit 1 ;;
37
- esac
38
- done
39
-
40
- if [[ -z "$SOURCE_ROOT" || -z "$TARGET_ROOT" || -z "$PATHS_FILE" ]]; then
41
- usage >&2
42
- exit 1
43
- fi
44
-
45
- for required_path in "$SOURCE_ROOT" "$TARGET_ROOT" "$PATHS_FILE"; do
46
- [[ -e "$required_path" ]] || { echo "missing path: $required_path" >&2; exit 1; }
47
- done
48
-
49
- if [[ ! -d "$SOURCE_ROOT/.git" && ! -f "$SOURCE_ROOT/.git" ]]; then
50
- echo "source is not a git checkout: $SOURCE_ROOT" >&2
51
- exit 1
52
- fi
53
- if [[ ! -d "$TARGET_ROOT/.git" && ! -f "$TARGET_ROOT/.git" ]]; then
54
- echo "target is not a git checkout: $TARGET_ROOT" >&2
55
- exit 1
56
- fi
57
-
58
- if [[ -n "$(git -C "$TARGET_ROOT" status --short)" ]]; then
59
- echo "target worktree must be clean before splitting: $TARGET_ROOT" >&2
60
- exit 1
61
- fi
62
-
63
- if [[ -z "$BACKUP_ROOT" ]]; then
64
- BACKUP_ROOT="$(mktemp -d "${TMPDIR:-/tmp}/retained-slice-backup.XXXXXX")"
65
- else
66
- mkdir -p "$BACKUP_ROOT"
67
- fi
68
-
69
- copy_path() {
70
- local source_path="${1:?source path required}"
71
- local dest_root="${2:?destination root required}"
72
- local rel_path="${3:?relative path required}"
73
-
74
- if [[ -d "$source_path" ]]; then
75
- mkdir -p "$(dirname "${dest_root}/${rel_path}")"
76
- rm -rf "${dest_root}/${rel_path}"
77
- cp -R "$source_path" "${dest_root}/${rel_path}"
78
- else
79
- mkdir -p "$(dirname "${dest_root}/${rel_path}")"
80
- cp -p "$source_path" "${dest_root}/${rel_path}"
81
- fi
82
- }
83
-
84
- tracked_path_exists() {
85
- local repo_root="${1:?repo root required}"
86
- local rel_path="${2:?relative path required}"
87
- git -C "$repo_root" ls-files --error-unmatch -- "$rel_path" >/dev/null 2>&1
88
- }
89
-
90
- while IFS= read -r rel_path || [[ -n "$rel_path" ]]; do
91
- [[ -n "$rel_path" ]] || continue
92
- [[ "$rel_path" != \#* ]] || continue
93
-
94
- source_path="${SOURCE_ROOT}/${rel_path}"
95
- [[ -e "$source_path" ]] || { echo "source path missing: $rel_path" >&2; exit 1; }
96
-
97
- copy_path "$source_path" "$BACKUP_ROOT" "$rel_path"
98
- copy_path "$source_path" "$TARGET_ROOT" "$rel_path"
99
-
100
- diff -qr "$source_path" "${TARGET_ROOT}/${rel_path}" >/dev/null
101
- done <"$PATHS_FILE"
102
-
103
- if [[ "$MOVE_MODE" == "true" ]]; then
104
- while IFS= read -r rel_path || [[ -n "$rel_path" ]]; do
105
- [[ -n "$rel_path" ]] || continue
106
- [[ "$rel_path" != \#* ]] || continue
107
-
108
- was_tracked="false"
109
- if tracked_path_exists "$SOURCE_ROOT" "$rel_path"; then
110
- was_tracked="true"
111
- git -C "$SOURCE_ROOT" restore --worktree --source=HEAD -- "$rel_path"
112
- fi
113
-
114
- if [[ "$was_tracked" != "true" && -e "${SOURCE_ROOT}/${rel_path}" ]]; then
115
- rm -rf "${SOURCE_ROOT:?}/${rel_path}"
116
- fi
117
- done <"$PATHS_FILE"
118
- fi
119
-
120
- printf 'SOURCE_ROOT=%s\n' "$SOURCE_ROOT"
121
- printf 'TARGET_ROOT=%s\n' "$TARGET_ROOT"
122
- printf 'PATHS_FILE=%s\n' "$PATHS_FILE"
123
- printf 'BACKUP_ROOT=%s\n' "$BACKUP_ROOT"
124
- printf 'MOVE_MODE=%s\n' "$MOVE_MODE"