From rapid
Merge completed sets into main -- subagent delegation per set, fast-path merge-tree, 5-level conflict detection, 4-tier resolution, adaptive conflict resolution via resolver agents, DAG-ordered merging, bisection recovery, rollback
npx claudepluginhub pragnition/pragnition-public-plugins --plugin rapidThis skill is limited to using the following tools:
You are the RAPID merge orchestrator. This skill merges completed set branches into main via subagent delegation per set. Each set is dispatched to an isolated rapid-set-merger subagent for 5-level conflict detection, 4-tier resolution cascade, and programmatic gate validation. Clean merges skip subagent dispatch entirely via git merge-tree fast path. You spawn subagents using the Agent tool an...
Searches, retrieves, and installs Agent Skills from prompts.chat registry using MCP tools like search_skills and get_skill. Activates for finding skills, browsing catalogs, or extending Claude.
Searches prompts.chat for AI prompt templates by keyword or category, retrieves by ID with variable handling, and improves prompts via AI. Use for discovering or enhancing prompts.
Checks Next.js compilation errors using a running Turbopack dev server after code edits. Fixes actionable issues before reporting complete. Replaces `next build`.
You are the RAPID merge orchestrator. This skill merges completed set branches into main via subagent delegation per set. Each set is dispatched to an isolated rapid-set-merger subagent for 5-level conflict detection, 4-tier resolution cascade, and programmatic gate validation. Clean merges skip subagent dispatch entirely via git merge-tree fast path. You spawn subagents using the Agent tool and collect structured RAPID:RETURN results. Follow these steps IN ORDER. Do not skip steps.
if [ -z "${RAPID_TOOLS:-}" ] && [ -n "${CLAUDE_SKILL_DIR:-}" ] && [ -f "${CLAUDE_SKILL_DIR}/../../.env" ]; then export $(grep -v '^#' "${CLAUDE_SKILL_DIR}/../../.env" | xargs); fi
if [ -z "${RAPID_TOOLS}" ]; then echo "[RAPID ERROR] RAPID_TOOLS is not set. Run /rapid:install or ./setup.sh to configure RAPID."; exit 1; fi
if [ -z "${RAPID_TOOLS:-}" ] && [ -n "${CLAUDE_SKILL_DIR:-}" ] && [ -f "${CLAUDE_SKILL_DIR}/../../.env" ]; then export $(grep -v '^#' "${CLAUDE_SKILL_DIR}/../../.env" | xargs); fi
if [ -z "${RAPID_TOOLS}" ]; then echo "[RAPID ERROR] RAPID_TOOLS is not set. Run /rapid:install or ./setup.sh to configure RAPID."; exit 1; fi
node "${RAPID_TOOLS}" display banner merge
node "${RAPID_TOOLS}" merge order
node "${RAPID_TOOLS}" merge status
node "${RAPID_TOOLS}" state get --all
Parse the merge order (wave-grouped arrays) and status. Identify which sets are ready to merge (status='complete' in STATE.json, mergeStatus=pending in MERGE-STATE). Check MERGE-STATE.json for each set to enable idempotent re-entry -- skip sets that are already status='complete' in MERGE-STATE.
For each set in the merge plan, check the registry for solo entries:
node "${RAPID_TOOLS}" worktree status --json
Parse the JSON output. For each worktree entry with solo: true, mark that set as a solo set. Solo sets will be fast-pathed in Step 3 (no subagent dispatch, no conflict detection).
In the merge plan display, annotate solo sets:
- Wave 1: {set-name} (solo -- auto-merge)
If a solo set is already in merged status in STATE.json (auto-merged after execution):
Set '{set-name}' is a solo set -- already merged automatically after execution. No merge needed. Next step:
/rapid:review {set-index} --post-merge
If the user specified a single solo set to merge and it is already merged, display this message and exit gracefully. Do not treat this as an error.
If a specific set name was provided (e.g., /rapid:merge auth-set or /rapid:merge 1):
Resolve the set argument through the numeric ID resolver:
# (env preamble here)
RESOLVE_RESULT=$(node "${RAPID_TOOLS}" resolve set "<user-input>" 2>&1)
RESOLVE_EXIT=$?
if [ $RESOLVE_EXIT -ne 0 ]; then
echo "$RESOLVE_RESULT"
# Display the error message from the JSON and STOP
fi
SET_NAME=$(echo "$RESOLVE_RESULT" | node -e "d=JSON.parse(require('fs').readFileSync(0,'utf-8')); console.log(d.resolvedId)")
Use SET_NAME for all subsequent operations. Then:
Show the user the merge plan:
Merge Plan:
- Wave 1: {set names} (sequential merge)
- Wave 2: {set names} (after Wave 1 integration gate)
- ...
Sets ready: {count} Sets not ready: {list with reasons} Sets already merged: {list, will be skipped}
Use AskUserQuestion to confirm:
If the developer selects "Cancel", print "Merge pipeline cancelled." and exit.
For each wave (in order), run Steps 3-8 for each set in the wave. Sets within a wave merge SEQUENTIALLY (not in parallel) -- each merge sees the result of the previous one.
Before starting each wave, record the pre-wave commit for potential bisection:
PRE_WAVE_COMMIT=$(git rev-parse HEAD)
Track merged sets per wave for integration gate and bisection.
Initialize two in-memory tracking structures at the start of each wave:
For each set in the current wave (sequential processing):
node "${RAPID_TOOLS}" merge merge-state {setName}
If status='complete', skip this set. Display:
[{waveNum}/{totalWaves}] {setName}: already merged (skipping)
If agentPhase1='done', skip to Step 6 (merge execute). Display:
[{waveNum}/{totalWaves}] {setName}: detection/resolution done, proceeding to merge
Before running merge-tree or dispatching a subagent, check if the set is a solo set via the registry:
If the set has solo: true in the registry:
[{waveNum}/{totalWaves}] {setName}: solo set (no merge needed)
Skip directly to Step 6 (merge execute). The merge execute CLI command (via mergeSet()) already handles solo sets by returning { merged: true, solo: true } immediately.
If the solo set is already in merged status in STATE.json:
[{waveNum}/{totalWaves}] {setName}: solo set already merged (skipping)
Skip this set entirely -- do not call merge execute. Solo sets that were auto-merged during execute-set do not need any merge operations.
git merge-tree --write-tree HEAD rapid/{setName}
Check the exit code:
Exit code 0: No conflicts. Skip subagent entirely. Display:
[{waveNum}/{totalWaves}] {setName}: clean merge (fast path)
Go directly to Step 6 (merge execute).
Exit code 1: Conflicts detected. Continue to 3c (dispatch subagent).
Exit code >1: Error. Continue to 3c (let subagent diagnose).
Update merge status and agent phase:
node "${RAPID_TOOLS}" merge update-status {setName} resolving --agent-phase spawned
Get launch briefing:
node "${RAPID_TOOLS}" merge prepare-context {setName}
Parse the JSON output to get the briefing string.
Display progress:
[{waveNum}/{totalWaves}] {setName}: dispatching rapid-set-merger subagent...
Spawn the rapid-set-merger agent with this task:
Merge set '{setName}' branch 'rapid/{setName}' into '{baseBranch}'.
## Launch Briefing
{briefing from prepare-context}
## Instructions
1. Run L1-L4 detection: `node "${RAPID_TOOLS}" merge detect {setName}`
2. If conflicts found, run T1-T2 resolution: `node "${RAPID_TOOLS}" merge resolve {setName}`
3. If unresolved conflicts remain, perform L5 semantic analysis and T3/T4 resolution inline (per your role instructions)
4. Run programmatic gate: `node "${RAPID_TOOLS}" merge review {setName}`
5. Return structured RAPID:RETURN with results
## Working Directory
{worktreePath}
## Return Format
<!-- RAPID:RETURN {"status":"COMPLETE","data":{"semantic_conflicts":[...],"resolutions":[...],"escalations":[...],"gate_passed":<boolean>,"all_resolved":<boolean>}} -->
Parse the agent's output using parseSetMergerReturn logic:
COMPLETE:
node "${RAPID_TOOLS}" merge update-status {setName} resolved --agent-phase done
node "${RAPID_TOOLS}" merge merge-state {setName}
compressedResults map.gate_passed field from the return data:
gate_passed is false: add to blockedSets with reason "programmatic gate failed". Continue to next set.gate_passed is true: continue to Step 3e.CHECKPOINT (attempt 1):
Auto-retry once with checkpoint data included in re-dispatch prompt:
Merge set '{setName}' branch 'rapid/{setName}' into '{baseBranch}'.
## Checkpoint (continuing from previous attempt)
- Done: {handoff.done}
- Remaining: {handoff.remaining}
- Resume from: {handoff.resume}
## Launch Briefing
{briefing from prepare-context}
## Instructions
1. Run L1-L4 detection: `node "${RAPID_TOOLS}" merge detect {setName}`
2. If conflicts found, run T1-T2 resolution: `node "${RAPID_TOOLS}" merge resolve {setName}`
3. If unresolved conflicts remain, perform L5 semantic analysis and T3/T4 resolution inline (per your role instructions)
4. Run programmatic gate: `node "${RAPID_TOOLS}" merge review {setName}`
5. Return structured RAPID:RETURN with results
## Working Directory
{worktreePath}
## Return Format
<!-- RAPID:RETURN {"status":"COMPLETE","data":{"semantic_conflicts":[...],"resolutions":[...],"escalations":[...],"gate_passed":<boolean>,"all_resolved":<boolean>}} -->
Parse the retry's return:
node "${RAPID_TOOLS}" merge update-status {setName} failed --agent-phase failed
BLOCKED or malformed:
node "${RAPID_TOOLS}" merge update-status {setName} failed --agent-phase failed
blockedSets with reason from parseSetMergerReturn (or "malformed return" if parsing failed).If return data contains escalations (conflicts from set-merger with confidence scores):
For each escalation in the return data:
file field as the ID. If multiple escalations share the same file, append :1, :2 suffix.detection.api.conflicts. If yes -> classify as human-api-gate (regardless of confidence).human-directresolver-agentauto-acceptGroup escalations into four buckets: resolverBound, humanApiGate, humanDirect, autoAccept.
For escalations classified as auto-accept (confidence > 0.8 that somehow reached escalation):
For escalations classified as resolver-agent:
node "${RAPID_TOOLS}" merge update-status {setName} resolving --agent-phase2 {conflictId} spawned
rapid-conflict-resolver agent using the Agent tool with prompt:
Resolve conflict '{conflictId}' in file '{file}' for set '{setName}'.
## Launch Briefing
{resolver context assembled above}
## Working Directory
{worktreePath}
## Return Format
<!-- RAPID:RETURN {"status":"COMPLETE","data":{"conflict_id":"...","strategies_tried":[{"approach":"...","confidence":0.X,"reason":"..."}],"selected_strategy":"...","resolution_summary":"...","confidence":0.X,"files_modified":["..."],"applied":true}} -->
ALL resolver Agent tool calls happen in the same response for parallel dispatch. Then collect all returns.
For each resolver return:
node "${RAPID_TOOLS}" merge update-status {setName} resolving --agent-phase2 {conflictId} done
humanEscalations list with the resolver's analysis, proposed resolution, and diff.node "${RAPID_TOOLS}" merge update-status {setName} resolving --agent-phase2 {conflictId} done
humanEscalations list with the failure reason.node "${RAPID_TOOLS}" merge update-status {setName} resolving --agent-phase2 {conflictId} failed
Combine all human-bound conflicts: humanApiGate + humanDirect + resolver escalations (confidence < 0.7 or BLOCKED).
For API-signature conflicts (humanApiGate):
For direct human conflicts (humanDirect -- confidence < 0.3):
For resolver-escalated conflicts (resolver confidence < 0.7):
After all resolvers complete and human decisions are made, re-run the programmatic gate to validate the combined changes:
node "${RAPID_TOOLS}" merge review {setName}
If the gate fails, present the failure to the user and offer to continue or abort.
After all escalations handled, proceed to Step 6 (merge execute).
After a set passes dispatch (COMPLETE with gate_passed=true, or fast path, or re-entry from agentPhase1=done):
node "${RAPID_TOOLS}" merge execute {setName}
Parse the JSON result:
If merged: true:
Auto-transition the set status to 'merged':
node "${RAPID_TOOLS}" state transition set <milestone> <setName> merged
[{waveNum}/{totalWaves}] {setName}: MERGED and status updated to 'merged' (commit {commitHash}) Tip: Run
/rapid:review {setIndex} --post-mergeto review this set's merged code.
Add this set to the wave's merged-sets list for integration gate tracking.
If merged: false, reason: 'conflict':
Merge conflict in set '{setName}' Conflicting files: {list}
Use AskUserQuestion:
If "Resolve manually":
Conflicting files: {file list}
To resolve:
- Edit the conflicting files to resolve markers
git add {files}git merge --continue
If "Show diff":
git diff and display outputIf "Abort pipeline":
If merged: false, reason: 'error':
Merge error for set '{setName}' Detail: {detail}
Use AskUserQuestion:
If "Retry merge": re-run node "${RAPID_TOOLS}" merge execute {setName} and re-parse.
If "Skip set": continue to next set.
If "Abort pipeline": exit.
If merged: false, reason: 'feature_regression':
Feature regression detected in set '{setName}' The merge was automatically reverted because exported symbols were lost. Detail: {detail}
Regressions: {for each regression in regressions: "-
{file}: lost exports [{missing joined by ', '}]"}
Use AskUserQuestion:
If "Investigate": display the regression details (base exports, set exports, merged exports for each file) and show git diff for affected files between preMergeHead and the set branch. Then present resolve/abort options.
If "Re-dispatch resolver": re-run Step 3c for this set with the regression data included in the launch briefing.
If "Force merge": re-run node "${RAPID_TOOLS}" merge execute {setName} -- but note the regression check will fire again. To truly force, the user must resolve the export loss first.
If "Abort pipeline": exit.
After all sets in the wave have been processed (dispatched + collected OR fast-pathed + merged):
If blockedSets is not empty, display the blocked summary:
Blocked sets in Wave {waveNum}: {for each blocked set: "- {setName}: {reason} ({attempts} attempt(s))"}
For each blocked set (max 2 total attempts per set across initial dispatch + retries):
Use AskUserQuestion:
If "Retry":
If "Skip": continue to next blocked set or integration gate. If "Abort": print "Merge pipeline cancelled." and exit.
After ALL sets in the current wave have been merged (or skipped), and blocked set recovery is complete:
node "${RAPID_TOOLS}" merge integration-test
If passed: true:
Wave {waveNum} integration gate: PASS All tests pass after merging Wave {waveNum} sets.
If there are more waves, use AskUserQuestion:
If "Pause pipeline": print "Merge pipeline paused after Wave {waveNum}. Resume with /rapid:merge." and exit.
If passed: false:
Wave {waveNum} integration gate: FAIL Tests failing after merging Wave {waveNum} sets. Output: {test output}
Auto-trigger bisection recovery (per user locked decision -- no pre-bisection AskUserQuestion):
Integration tests failed. Running bisection recovery automatically...
node "${RAPID_TOOLS}" merge bisect {waveNum}
Parse the bisection result and display:
Bisection result: Breaking set: {breakingSet} (found in {iterations} iterations)
Use AskUserQuestion:
If "Rollback breaking set": proceed to Step 7d (rollback).
If "Investigate manually": print "Pausing for investigation. Re-run /rapid:merge after fixing." and exit.
If "Abort pipeline": print "Merge pipeline cancelled. Wave {waveNum} merges remain." and exit.
If rollback requested for a set:
node "${RAPID_TOOLS}" merge rollback {setName}
Parse the JSON result:
If cascadeWarning: true (has dependent sets already merged):
Cascade impact detected: Dependent sets affected: {affectedSets} Recommendation: {recommendation}
Use AskUserQuestion:
If "Proceed with rollback": run node "${RAPID_TOOLS}" merge rollback {setName} --force and continue.
If "Cancel rollback": print "Rollback cancelled. Investigate manually." and exit.
If rolledBack: true:
{setName} reverted (commit: {revertCommit})
Run integration tests again to verify the rollback fixed the issue:
node "${RAPID_TOOLS}" merge integration-test
If tests pass:
Integration tests pass after rollback.
Continue to next wave.
If tests still fail:
Integration tests still failing after rollback.
Use AskUserQuestion:
If rolledBack: false:
Rollback failed for {setName}: {reason} Detail: {detail}
Use AskUserQuestion:
After all waves complete:
node "${RAPID_TOOLS}" merge status
Build the final summary from the in-memory compressedResults collected during Step 3d. For each set, the compressedResult contains: setId, status, conflictCounts (L1-L5), resolutionCounts (T1-T3, escalated), and commitSha.
Present final summary:
Merge Pipeline Complete
Set Status L1 L2 L3 L4 L5 T1 T2 T3 Escalated Commit {setId} {status} {L1} {L2} {L3} {L4} {L5} {T1} {T2} {T3} {escalated} {commitSha} Summary:
- Total sets merged: {count}
- Total waves: {count}
- Sets skipped (blocked): {list or "none"}
- Sets rolled back: {list or "none"}
- Sets fast-pathed (no conflicts): {count}
- Conflicts detected: {total across all sets}
- Conflicts auto-resolved (T1/T2): {count}
- Conflicts AI-resolved (T3): {count}
- Conflicts escalated (T4): {count}
- Bisection runs: {count or "none"}
Display the available next steps:
Next steps:
/rapid:review {setIndex} --post-merge-- Run post-merge review on merged sets (recommended)/rapid:cleanup-- Remove completed worktrees/rapid:status-- View project state/rapid:new-version-- Start planning next version (if all sets merged)
Display the completion footer:
if [ -z "${RAPID_TOOLS:-}" ] && [ -n "${CLAUDE_SKILL_DIR:-}" ] && [ -f "${CLAUDE_SKILL_DIR}/../../.env" ]; then export $(grep -v '^#' "${CLAUDE_SKILL_DIR}/../../.env" | xargs); fi
if [ -z "${RAPID_TOOLS}" ]; then echo "[RAPID ERROR] RAPID_TOOLS is not set. Run /rapid:install or ./setup.sh to configure RAPID."; exit 1; fi
node "${RAPID_TOOLS}" display footer "/rapid:cleanup" --breadcrumb "init [done] > start-set [done] > discuss-set [done] > plan-set [done] > execute-set [done] > review [done] > merge [done]"
solo: true in the registry. Solo sets are auto-merged to merged status during execute-set Step 6. If a user runs /rapid:merge on a solo set, the pipeline detects the merged status and displays an informational message: "Set '{name}' is a solo set -- already merged automatically after execution. No merge needed." The merge execute command also handles solo sets gracefully by returning { merged: true, solo: true } immediately without git operations. No subagent is dispatched, no conflict detection runs, no integration tests are needed for solo-only waves.git merge-tree --write-tree HEAD rapid/{setName} checks for conflicts without touching the index or working tree. Exit code 0 means clean merge -- skip subagent entirely. This is the common case for well-isolated sets.update-status --agent-phase CLI calls. Transitions: idle -> spawned (before dispatch) -> done/failed (after return). No path should leave a set as 'spawned' after dispatch completes.update-status --agent-phase2 <conflictId> <phase> CLI calls. agentPhase2 is an object map { [conflictId]: 'idle'|'spawned'|'done'|'failed' } tracking each conflict independently./rapid:merge invocation starts fresh. Resolver agents do NOT retry -- failed resolvers escalate to human immediately (they are already a second pass).git add -A or git add . -- stage only specific files.merge execute returns merged: true, the orchestrator runs state transition set to move the set to 'merged' status in STATE.json./rapid:review <set> --post-merge for post-merge review. This is optional but recommended to catch integration issues and verify merge correctness. Post-merge review scopes files from the merge commit diff and does not require a worktree.git merge --no-ff, the mergeSet() function automatically detects and commits any untracked files under .planning/ on the base branch. This prevents merge failures caused by stale planning artifacts (WAVE-COMPLETE.md, PLAN-DIGEST.md, etc.) that were created during execution and landed on main as untracked files. The cleanup scopes to .planning/ only and handles artifacts from ALL sets, not just the merging set.