| name | amend-plan |
| description | Adjust an existing implementation plan in `ai-plans/` after implementation has started or finished. Updates the plan file (revising existing phases or appending new ones), then for each affected phase that was already implemented adjusts its commits (`git commit --amend` or new commits) on the phase branch, force-pushes the rewritten branch, rebases every downstream stacked phase branch, force-pushes each, and refreshes the PR-context files. Use when the user says "amend the plan", "update phase N", "add a phase to plan X", "the spec changed, fix the plan", or "rewrite the implementation for phase N". NOT for one-off changes to a single file unrelated to a plan; use the regular implement skill for that. Agents push branches and open PRs via `gh` after review passes. |
Amend Plan
Revise a plan in ai-plans/ after work has begun. Companion conductor to implement-plan: it reuses the same sub-skills (implement-phase for the body change, review-phase for the gates) — but the orchestrator's job here is history rewriting instead of forward execution.
The flow is destructive (force-push). Every modification is gated on user confirmation. Default disposition for any ambiguous case is "stop and ask" — never force-push without an explicit per-branch Confirm from the user.
Unsupported commit strategy
Before doing anything else, resolve this plan's commit strategy. This project's policies.commit_strategy is ask, so the strategy is chosen per run and cached in ai-plans/TRACKING_{plan-id}.md under run_options.commit_strategy_resolved. Read that value first.
run_options.commit_strategy_resolved = stacked-branches (or the tracking file is absent and the user confirms the plan was run stacked) → this section does not apply. Proceed with the full amend flow below.
run_options.commit_strategy_resolved = modular-commits → refuse. This skill does not yet support amending under modular commits.
Amending under modular commits requires rewriting an arbitrary number of inline atomic commits across a shared plan/{plan-id-kebab} branch. The git topology is fundamentally different from the per-phase stacked branches this skill is designed around — the rewrite plan, force-push targets, and downstream rebase fan-out all differ. Full support is tracked as a follow-up.
Resolve the amendment one of three ways:
- Append a new phase — extend the plan with the change as a new
Phase N+1, then run implement-plan. Cleanest path; preserves the existing commit log.
- Hand-craft the amendment —
git rebase -i plan/{plan-id-kebab} (or git commit --fixup + git rebase --autosquash) on the plan branch, force-push, and re-run review manually. Skip this skill entirely.
- Re-run the plan from scratch on a new branch — abandon the in-flight commits (leave them for audit), regenerate the plan with plan-feature, implement forward.
Refuse with this guidance; do not proceed.
Working assumptions
-
Repo: vinta-schedule-frontend-web (Next.js 16 App Router + React 19 + TypeScript strict; Tailwind v4 with tokens in the vinta-schedule-design-system pnpm-workspace package (shadcn/ui atoms + layout primitives); TanStack Query v5 over hey-api generated OpenAPI clients; react-hook-form + zod; Vitest + Testing Library; Playwright e2e; two Storybooks; deployed to Vercel via tag-driven CI). Conventions: AGENTS.md.
-
Plan files: ai-plans/YYYY-MM-DD-FEATURE_NAME_PLAN.md.
-
Lint: pnpm run lint. Format: pnpm run format.
-
Type / build gate: pnpm run typecheck — runs tsc --noEmit for the app and pnpm --filter vinta-schedule-design-system typecheck for the design-system package. (pnpm run build is the Vercel deploy build, not the per-phase gate.) No CI job runs lint / typecheck / tests in this repo — the GitHub workflows only deploy. This local gate is the only gate.
-
Unit / integration tests: pnpm run test — pnpm run test runs vitest run for the app plus pnpm --filter vinta-schedule-design-system test for the design system; scope with pnpm vitest run <path-or-pattern>, or pnpm --filter vinta-schedule-design-system test for design-system-only work.
-
E2E: Playwright, config at playwright.config.ts (testDir e2e/tests, chromium, baseURL from E2E_BASE_URL, default http://localhost:3000). There is no test:e2e npm script — invoke Playwright directly: npx playwright test (all), npx playwright test <path> (one spec), npx playwright install chromium (first run on a machine). Specs live at e2e/tests/app/<ID>-<slug>.spec.ts and map 1:1 to ids in QA_USE_CASES.md (PR### = member, PA### = admin). Tests hit a live backend — no mocking layer; they need NEXT_PUBLIC_API_BASE_URL + E2E_MEMBER_ACCESS_TOKEN / E2E_ADMIN_ACCESS_TOKEN to pass. Screenshots: specs call basePage.screenshot('<id>', '<NN>', '<slug>'); node e2e/scripts/collect-screenshots.mjs copies them into pr-screenshots/ (gitignored). See add-e2e-test + e2e/README.md.
-
Code host: GitHub. PR creation policy: agents create PRs — after a phase passes review, the orchestrator pushes the branch and opens the PR itself via the prs-context file + the bundled open-pr.sh (which shells out to gh).
-
AI co-author trailers are FORBIDDEN in this repo. No commit, PR body, or PR comment may carry Co-Authored-By: Claude, Co-Authored-By: <any AI>, Generated with Claude Code, or any equivalent AI-attribution trailer. This applies to every agent in the pipeline.
-
Default branch: main.
-
Branch naming convention (set by implement-plan): plan/{plan-id-kebab}/phase-{phase.id}.
-
WORKROOT. Resolve once, same as the implement-plan Resolve WORKROOT step: the main checkout by default, or the plan's worktree when run_options.use_worktree = true in the tracking file. Every git call below runs with git -C <WORKROOT>; when no worktree is in play, WORKROOT is the main checkout and the commands read exactly as in-place git.
When to use
- A spec change forces a phase body rewrite (different acceptance, different decisions in the plan's Guiding Decisions).
- A phase was implemented but the resulting diff is wrong / incomplete (caught post-merge to the phase branch but pre-merge to
main).
- A new phase needs to slot in between two existing ones, or be appended.
- A guiding decision in Guiding Decisions changed and it cascades into multiple phases.
When NOT to use
- Phase already merged to
main. History cannot be retroactively rewritten on main. The change must go in as a new phase appended to the plan, implemented forward via implement-plan. This skill detects this case and refuses to force-push a merged branch.
- Single-file change unrelated to a plan. Use the regular implement skill / direct edit.
- The plan never started. No commits to amend; just edit the plan file and run implement-plan normally.
Step 0 — Understand the change + parse the plan
-
Identify the plan file. Same logic as the implement-plan "Locate + parse plan" step: ask the user (path or feature name); ls ai-plans/ + grep; confirm before proceeding.
-
Capture the requested change. The user's prompt is the source. If vague, interview via AskUserQuestion:
- "Which phases are affected?" — enumerate phase ids from the plan's Phased Rollout section.
- "Is this a body rewrite of an existing phase, a new phase to slot in, or a Guiding Decisions change that cascades?"
- "What's the new acceptance criterion / change list?" — verbatim.
Don't infer scope. The plan-amend is the user's contract, not yours.
-
Parse the plan. Same structured fields as implement-plan's "Extract structured fields" step: plan id, Goals + Non-goals / Guiding Decisions / Data Model Changes / phase records from Phased Rollout / Risk & Rollout Notes through Touch List.
-
Read the tracking file ai-plans/TRACKING_{plan-id}.md if present. Its Completed Phases section tells you which phase branches were pushed, which model + base were used, and the run_options (including worktree state → WORKROOT). If absent → git -C <WORKROOT> branch -a | grep plan/{plan-id-kebab} to enumerate pushed phase branches.
-
Build a per-phase state map. For every phase in the plan, record:
| Field | Source |
|---|
phase.id, phase.title | plan's Phased Rollout section |
state | one of not-started / in-progress / implemented-not-merged / merged-to-default |
branch | tracking file or git, pattern plan/{plan-id-kebab}/phase-{id} |
base | tracking file or git -C <WORKROOT> merge-base origin/<branch> <prev-branch>; root phase bases on main |
pr_status | .vinta-ai-workflows/prs-context/{feature-kebab}/phase-{id}.md frontmatter (pending / published) when the file exists |
merged_to_default | `git -C branch --merged origin/main |
merged-to-default = true blocks any commit rewrite for that phase — see Step 3 — Refuse force-pushes that can't work below.
-
Classify the requested change by phase impact, in priority order:
body-rewrite — existing phase keeps its id; body changes. Cascades downstream because rewritten commits get new SHAs.
insert-new — new phase between existing ones. Cascades downstream because every later phase rebases onto the new branch.
append-new — new phase tacked on after the last one. No downstream cascade. Implementation runs forward via implement-plan — this skill hands off after editing the plan file.
guiding-decisions-change — change inside the plan's Guiding Decisions section. Cascades into every phase that referenced the decision.
-
Evaluate amendment blast radius — recommend restart when too big. Amending in place stops being a good deal once the rewrite work approaches re-implementation. Compute these signals from the per-phase state map + the requested change:
| Signal | Threshold suggesting RESTART |
|---|
Phases needing body-rewrite ÷ total implemented phases | ≥ 50% |
guiding-decisions-change cascading into | ≥ 50% of implemented phases |
Phases in merged-to-default (immutable, must be append-new) | ≥ 2, AND remaining work also rewrites earlier phases |
| New body materially changes the data-model contract from Data Model Changes | rewrite of >2 phases hinges on it |
| Estimated touched LoC across rewrites | ≥ 70% of original implementation diff size (rough estimate via git -C <WORKROOT> diff --stat <base>..<branch> summed across affected branches) |
| Multi-author phase branches in the rewrite queue | ≥ 1 (force-push erases collaborator local state) |
| Approved PRs in the rewrite queue | ≥ 2 (re-review burden becomes non-trivial) |
Any two signals tripping → mark the amendment as high-blast-radius. Three or more → mark as restart-recommended.
When high-blast-radius or restart-recommended, surface to the user via AskUserQuestion before showing the standard step-8 confirmation:
- "This amendment looks large enough that restarting from scratch may cost less than rewriting in place. Tripping signals: . Restarting means: rewrite the plan as a fresh
YYYY-MM-DD-FEATURE_NAME_PLAN.md (today's date), abandon the current phase branches (leave them in place for audit), run implement-plan on the new plan from scratch. Amending in place keeps history but force-pushes branches and re-spawns implementer/reviewer/fixer agents per phase."
Options:
Restart — draft a new plan, abandon current branches
Amend in place — proceed knowing the cost (you'll show me the force-push plan next)
Stop — let me think / talk to the team first
On Restart:
- Help the user draft a new
YYYY-MM-DD-FEATURE_NAME_PLAN.md with today's date (paired with the spec, same FEATURE_NAME). This skill does not write the new plan body — point at plan-feature (or create-spec first if the spec also changed).
- Annotate the old plan: at the top, add
**Superseded YYYY-MM-DD by ../YYYY-MM-DD-FEATURE_NAME_PLAN.md** — reason: <one line>. Append the same line under ## Amendments.
- Leave the old phase branches alone — useful audit trail, no force-push needed.
- Update
TRACKING_{plan-id}.md to mark the plan superseded; preserve all completed-phase entries.
- Hand off to plan-feature. This skill exits.
On Amend in place: proceed to step 8 (the original confirmation gate, renumbered). On Stop: exit cleanly; nothing written.
When the signals show low-blast-radius (≤1 tripping), skip the recommendation entirely and go straight to step 8. Don't pad easy amendments with restart questions.
-
Confirm with user before any write. Show: requested change, classified type, list of affected phase branches with their state + merge status, downstream branches that will be rebased, the force-push plan. Use AskUserQuestion:
Proceed — I authorize the force-pushes listed
Refine — let me adjust scope (loop back to step 2)
Stop
Anything in merged-to-default state shown explicitly with a warning. Do not include those in the force-push list — user must convert those to append-new phases instead.
Step 1 — Edit the plan file
Always the first write. Plan file is durable; commits get rewritten next.
-
Body rewrites — replace the affected ## Phase {id} block inside Phased Rollout verbatim with the new body. Keep phase.id stable so branch naming stays valid.
-
Inserts — choose a new id. Two conventions are common:
- Decimal:
1.5 between 1 and 2 (matches existing patterns in some Vinta plans). Branch becomes plan/{plan-id-kebab}/phase-1.5.
- Letter:
1b between 1 (relabeled 1a) and 2. Requires renaming 1 → 1a inside Phased Rollout + updating downstream references.
Ask the user. Default: decimal — no rename of existing ids.
-
Appends — new ## Phase N+1 block at end of Phased Rollout. Same shape as siblings: Goal, Suggested AI model, optional Review models, reusable_skills, Changes, Tests, Acceptance.
-
Guiding Decisions changes — rewrite the affected row. Add a one-line note at the top of Guiding Decisions ("Amended YYYY-MM-DD: replaced storage shape from X to Y; affects phases 2, 3, 4.") so reviewers see what shifted. Reference the changed row by its Decision column name, not by a §N.M shorthand.
-
Bump the amendment log. At the bottom of the plan, under ## Amendments, append:
- **YYYY-MM-DD** — <one-line summary of change>. Affected phases: <ids>. Branches force-pushed: <branch-list>.
Create the section if it doesn't exist. This is the audit trail; preserve every entry.
-
Commit the plan edit on main (or wherever the plan file lives — the plan file itself is not branched per phase). Commit message: Amend plan: <summary>. This repo uses Conventional Commits: type(scope): subject — e.g. feat(team): add invitations datatable, fix(auth): refresh token before retry, chore(client): regenerate hey-api output. Types in use: feat, fix, refactor, chore, docs, test.
Step 2 — Build the rewrite queue
For each phase classified as needing commit rewrites (body-rewrite for already-implemented phases, downstream phases for insert-new / body-rewrite / guiding-decisions-change), build a queue ordered by branch stack depth: parent first, children after.
For each entry record:
branch, base (parent in the stack — may be main or another phase branch).
change_kind: amend-existing (modify the phase body's effect on the diff) or rebase-only (parent moved, no body change for this phase).
commits_to_amend: list of SHAs the orchestrator may rewrite (look at git -C <WORKROOT> log <base>..<branch>).
Phases in not-started state are deferred to implement-plan — not rewritten here.
Step 3 — Refuse force-pushes that can't work
Before any write to remote, block on these conditions:
-
Phase merged to main. History on main is immutable in practice. Tell the user: "Phase X already merged to main. The amendment must be a new phase appended to the plan, not a rewrite. Re-run with classification append-new and execute via implement-plan."
-
Branch's PR was reviewed and approved. Force-pushing destroys reviewer context. Surface: list approved PRs by URL, ask AskUserQuestion:
Proceed — I'll re-request review after force-push
Stop — too disruptive, redesign as forward phase
-
Branch protection rules block force-push. gh api repos/{owner}/{repo}/branches/{branch}/protection (or glab equivalent). If the branch is protected, force-push will fail noisily — surface the rule, stop.
-
Multiple authors on the branch. git -C <WORKROOT> log --pretty=format:%ae <base>..<branch> | sort -u | wc -l > 1 → other developers committed too. Force-push erases their local state. Surface, require explicit Yes, I've coordinated with <names> confirmation.
If any block triggers and the user can't dismiss it: stop. Don't proceed further. Tell the user the rewrite path is unavailable; suggest an append-new phase as the fallback.
Step 4 — Per-phase rewrite loop
For each entry in the rewrite queue, in stack order:
4a. Check out the branch
git -C <WORKROOT> fetch origin
git -C <WORKROOT> checkout {branch}
git -C <WORKROOT> reset --hard origin/{branch}
4b. For change_kind = amend-existing only — apply the body change
Spawn an implementer subagent. The prompt mirrors implement-phase but records the change differently (new commit on top by default, never a push). Compose:
You are amending {phase.id}: {phase.title} of plan {plan.id}.
## Repo
vinta-schedule-frontend-web (Next.js 16 App Router + React 19 + TypeScript strict; Tailwind v4 with tokens in the `vinta-schedule-design-system` pnpm-workspace package (shadcn/ui atoms + layout primitives); TanStack Query v5 over hey-api generated OpenAPI clients; react-hook-form + zod; Vitest + Testing Library; Playwright e2e; two Storybooks; deployed to Vercel via tag-driven CI).
## Working location
Work inside `<WORKROOT>`. `cd` into it before any command.
## Read first
1. AGENTS.md — repo conventions.
2. ai-plans/{plan-filename}, the **Goals + Non-goals**, **Guiding Decisions**, and **Data Model Changes** sections, plus the rewritten phase body inside **Phased Rollout**.
3. The current diff: `git -C <WORKROOT> diff {base}...HEAD` — what's already on this branch.
## What changed in the plan (verbatim)
{Diff between old phase body and new — produce via `diff <(old-body) <(new-body)`. Or, if the plan was rewritten in place, the new body verbatim with a note "this replaces what was here before".}
## Your task
Bring the diff on this branch into compliance with the new phase body. You may:
- Edit existing files this branch already modified.
- Add new files when the new body requires them.
- Remove files this branch added that the new body no longer needs.
## How to record the change
Default: ADD A NEW COMMIT on top of the existing branch. Title: "Amend phase {phase.id}: <summary>". This preserves the original implementation as a separate commit and makes the amendment auditable in `git log`.
Use `git commit --amend` ONLY when:
- The branch has exactly one commit, AND
- The amendment is small (≤30% of the original diff size), AND
- The user explicitly authorized amend in Step 0.
## Adding new third-party dependencies
Before running any install command (`pnpm add`, `npm add`, `yarn add`, equivalents), check the package's SPDX license against the project's forbidden list — see the **Dependency licenses** section in [AGENTS.md](AGENTS.md) for the full list, the per-package overrides, and any project-specific notes. Enforcement mode for this project is **block**. Forbidden: `GPL-2.0-only`, `GPL-3.0-only`, `AGPL-3.0-only`, `SSPL-1.0`.
Quick lookup:
- **npm / pnpm / yarn**: `npm view <pkg> license`.
- No license field / a bare `LICENSE` file with no SPDX id → treat as unknown; see below.
If the license is in the forbidden list AND the `(package, license)` pair is **not** listed under **Approved overrides** in AGENTS.md:
1. Stop. Do not run the install command.
2. Surface the violation to the user with: package name, SPDX identifier, why it's forbidden, link to the upstream license.
3. Offer alternatives (search the ecosystem for an MIT / Apache-2.0 / BSD-licensed equivalent) before asking for an override.
4. If the user grants a one-off override, the orchestrator must record it in `policies.dependency_licenses.allowed_overrides[]` of `.vinta-ai-workflows.yaml` (package + SPDX + one-line reason) before re-running the install. Undocumented overrides leak into the diff and the reviewer agent will flag them.
**License unknown / undeclared.** When the lookup above returns no license, an empty value, `UNKNOWN`, `SEE LICENSE IN <file>`, or only an unstructured `LICENSE` file in the repo with no SPDX identifier, treat it as a **policy decision the user owns** — don't guess, don't auto-infer, don't fall back to "assume MIT". The package may be unlicensed (all-rights-reserved by default in most jurisdictions), proprietary, or simply missing metadata.
1. Stop. Do not run the install command.
2. Surface to the user: package name, what was found (e.g. "the `license` field is absent in `package.json`", "no LICENSE file in the repo"), the upstream repo / registry URL so the user can verify.
3. Ask via `AskUserQuestion`: `Skip — find a licensed alternative`, `Treat as forbidden — refuse install`, `Treat as allowed — record an override` (the third option only when the user has independently confirmed the license off-channel; record the resolved SPDX in `allowed_overrides[]` with the source in the `reason` field).
4. Don't add the dep until the user picks one of the three.
Transitive deps follow the same rule, but checking every transitive license at install time is impractical — a separate license-audit run handles the deep walk. **Note: no CI job audits licenses in this repo**, so the direct add you are about to make is the only checkpoint. The subagent's responsibility is the **direct** add.
Then splice in the shared inner/outer verification loop verbatim:
Working instructions
- Read existing code paths your changes touch — do not write before reading.
- Implement using Read/Edit/Write. Match existing patterns.
- Inner loop — fast iteration. Scoped to files/apps you touched:
a.
pnpm run lint until clean.
b. pnpm vitest run <new-test-path> for new tests individually.
c. Scoped suite: pnpm vitest run <path-or-pattern> (app), pnpm --filter vinta-schedule-design-system test (design system).
- Iterate 2–3 until new tests pass individually and the scoped suite is green. Do not advance to step 5 with red scoped tests.
- Outer gate — local verification, only after step 4 is green. All MUST pass before staging:
a. Type / build:
pnpm run typecheck — repo-wide, always.
b. Tests: by default run only the scoped suite ``pnpm vitest run (app),pnpm --filter vinta-schedule-design-system test (design system) for the apps/files you touched — the new tests already passed individually in step 4b, so this re-confirms the touched surface without paying for the whole repo.
{If run_options.full_test_suite = true:} run the full test suite pnpm run test instead of the scoped suite — this phase guards against regressions in untouched code too.
c. E2E (opt-in): {If run_options.run_e2e = true:} when this phase has an e2e spec, run npx playwright test e2e/tests/app/<ID>-<slug>.spec.ts and then copy screenshots into pr-screenshots/ via node e2e/scripts/collect-screenshots.mjs. {Else:} skip e2e this run (default — e2e boots a browser against a live backend and makes the phase take a lot longer).
- Outer gate fails → return step 2 (fix regression), re-run inner loop, then 5a/5b/5c. Never commit, push, or proceed while any gate is red.
…and close the prompt with the amend-specific staging tail:
7. Stage explicitly: `git add <explicit paths this phase touched — e.g. `src/... packages/design-system/src/... e2e/... ai-plans/...`>`.
8. Commit. This repo uses **Conventional Commits**: `type(scope): subject` — e.g. `feat(team): add invitations datatable`, `fix(auth): refresh token before retry`, `chore(client): regenerate hey-api output`. Types in use: `feat`, `fix`, `refactor`, `chore`, `docs`, `test`.
9. **Do NOT add any AI co-author trailer.** No `Co-Authored-By: Claude`, no `Generated with …` line, no AI attribution of any kind in the commit message.
10. **Do NOT push. Do NOT force-push.** The orchestrator owns the remote.
## Required output
- Status: SUCCESS or FAILURE.
- New commit SHA(s) added (or amended SHA).
- 5–15 line summary.
- Deviations from new body + reasoning.
For change_kind = rebase-only (downstream phase whose parent moved): skip the agent. The work is purely git topology.
4c. Run the three-layer review
Invoke review-phase against the rewritten branch, passing the new phase body to walk against, WORKROOT, and the reviewer / fixer agent types with their agent_models tiers plus this phase's reviewer_model_tier / fixer_model_tier overrides (parsed from the rewritten body's **Review models**: line, null when absent). Layer 2 walks: every "Changes" item in the new body, every "Tests" entry, the new acceptance line.
Skip this step only when change_kind = rebase-only (no body change → no compliance walk). Even then, spot-run review-phase's Layer 1 mechanical checks to verify the rebase didn't lose unrelated work.
4d. Rebase onto the (possibly-rewritten) parent
git -C <WORKROOT> fetch origin
PARENT_TIP=$(git -C <WORKROOT> rev-parse origin/{base})
git -C <WORKROOT> rebase $PARENT_TIP
Conflicts:
- Spawn a fixer subagent with the conflict body + new phase body + parent's tip diff. Same fixer agent type as review-phase.
- Fixer resolves, runs inner + outer gate (in
<WORKROOT>).
- Orchestrator continues the rebase:
git -C <WORKROOT> rebase --continue.
Repeat until the rebase finishes clean. If the fixer can't resolve after one retry → stop. Surface to user; do not push a half-rebased branch.
4e. Force-push (with confirmation)
AskUserQuestion:
Force-push <branch> now (was authorized in Step 0)
Pause — let me look at the local state first
On confirm:
git -C <WORKROOT> push --force-with-lease origin {branch}
Use --force-with-lease, not --force. It refuses to overwrite if the remote moved since the last fetch — protects against another developer's pushes the orchestrator didn't see.
If --force-with-lease rejects: another developer pushed. Stop. Re-fetch, re-apply, re-confirm.
4f. Refresh the PR-context file (when present)
For the rewritten branch, look for .vinta-ai-workflows/prs-context/{feature-kebab}/phase-{phase.id}.md:
- File missing — skip; nothing to refresh.
- File
status: pending — rewrite the file to reflect new title / description / comments per the prs-context-template. Status stays pending. The user will publish later via open-pr-from-context.
- File
status: published — the existing PR is auto-updated by the force-push (GitHub/GitLab pick up the new tip). But:
- Inline comments may now reference SHAs that no longer exist. They'll appear as "outdated" in the PR UI.
- If the new diff has materially different comment-worthy spots, regenerate the
# Comments block, set status: pending, and re-run open-pr.sh on the file. The script reuses the existing PR, posts new comments. Old "outdated" comments stay visible in the PR for audit; that's the platform's behavior.
When rewriting the # Description body, honor project.pr_template_paths from .vinta-ai-workflows.yaml — same rule as integrate-phase's Open PR via context file step: follow the project's PR template structure, fill new sections with phase-specific content from the rewritten body, leave un-fillable placeholders untouched. If the prior file used a different template than the project now declares, prefer the current pr_template_paths choice — surface the change to the user when the body shape shifts visibly.
Always include in the publish-log block at the bottom of the file:
- YYYY-MM-DDThh:mm:ssZ — branch force-pushed (amend-plan); old SHA <x>, new SHA <y>
4g. Update tracking file
Update ai-plans/TRACKING_{plan-id}.md for the rewritten phase:
- Append to its
Completed Phases entry: Amended YYYY-MM-DD: <summary>; new SHA <x>; force-pushed.
- Don't remove the original summary — keep history.
Step 5 — Final report
After every queue entry processes:
-
Print a per-branch summary:
plan/{plan-id-kebab}/phase-1 amended (commits added: 1; force-pushed)
plan/{plan-id-kebab}/phase-2 rebased (no body change; force-pushed)
plan/{plan-id-kebab}/phase-3 rebased (no body change; force-pushed)
plan/{plan-id-kebab}/phase-4 pending (not yet implemented; will use new parent next implement-plan run)
-
List any PR-context files now at status: pending that need re-publishing.
-
List any phases blocked from rewrite (Step 3 refusals) with the recommended forward path.
-
Reminder: reviewers on existing PRs need a re-review request — force-push erases context. Send a short comment on each affected PR (the orchestrator can do this via the PR CLI if the project's PR policy = "agents create PRs"; otherwise hand off to the human).
Important rules
- Never
--force. Always --force-with-lease. Protects against silent overwrites.
- Plan file edit is the first write. Commit the new plan body before any branch rewrite. The plan is the contract; the branches are the artifact.
- Recommend restart when blast radius is high. The blast-radius step inside Step 0 evaluates signals; ≥2 tripping signals → surface a restart option to the user before any force-push plan is shown. Don't quietly amend a half-rewrite of the whole plan.
- Never use
§N shorthand to point at sections — neither in this skill body, the rewritten plan body, the amendment log entry, nor any prs-context refresh. Always use the section's full name (and link when possible).
- Phases merged to
main are immutable. Convert to append-new phases. Refuse to attempt rewrites.
- Confirm every force-push individually. No batch "confirm all".
WORKROOT is resolved once, used everywhere. Every git call takes git -C <WORKROOT>; no per-step worktree branching.
- Three-layer review on every rewritten branch. Same standard as implement-plan — via review-phase. The amendment isn't done until Layer 3 passes.
- PR-context file is a derived artifact. Refresh it after the rewrite; never edit the file as a substitute for fixing the diff.
- Subagents commit but never push. Orchestrator owns force-push. or open PRs.
- Never write AI co-author trailers. Not in commits, not in PR bodies, not in PR comments.
Co-Authored-By: Claude / Generated with Claude Code are forbidden in this repo — Layer 1 of review-phase greps for them and blocks the phase on a hit.
- License check before any new dep. Refuse
pnpm add / npm add / yarn add when the package's SPDX license is in the forbidden list (GPL-2.0-only, GPL-3.0-only, AGPL-3.0-only, SSPL-1.0) — see AGENTS.md Dependency licenses. User can grant a one-off override after acknowledging the violation; record the override in policies.dependency_licenses.allowed_overrides before re-running.
- Stop on Tier-4 failure (model escalation, same rules as implement-phase).
- Stop on rebase failure the fixer can't resolve in one retry. Don't ship half-rebased branches.
Quick checklist (orchestrator, per amendment run)
What this skill does NOT do
- Does not execute new (
not-started) phases. That's implement-plan's job. Edit the plan, then hand off.
- Does not rewrite history on
main. Refuses up front.
- Does not auto-bypass branch protection. Surface the rule, stop.
- Does not amend commits made by humans on the branch unless explicitly authorized. Multi-author branches require explicit confirmation.
- Does not delete the plan file or its branches even when an amendment makes some phases obsolete. Mark obsolete phases in the plan body with
**Superseded YYYY-MM-DD by phase {new-id}**; leave their branches alone (or let the user delete manually).