| 1 | # Issue Lifecycle — Repo Connection & PR Flow |
| 2 | |
| 3 | Reference for connecting Squad to a repository and managing the issue→branch→PR→merge lifecycle. |
| 4 | |
| 5 | ## Repo Connection Format |
| 6 | |
| 7 | When connecting Squad to an issue tracker, store the connection in `.squad/team.md`: |
| 8 | |
| 9 | ```markdown |
| 10 | ## Issue Source |
| 11 | |
| 12 | **Repository:** {owner}/{repo} |
| 13 | **Connected:** {date} |
| 14 | **Platform:** {GitHub | Azure DevOps | Planner} |
| 15 | **Filters:** |
| 16 | - Labels: `{label-filter}` |
| 17 | - Project: `{project-name}` (ADO/Planner only) |
| 18 | - Plan: `{plan-id}` (Planner only) |
| 19 | ``` |
| 20 | |
| 21 | **Detection triggers:** |
| 22 | - User says "connect to {repo}" |
| 23 | - User says "monitor {repo} for issues" |
| 24 | - Ralph is activated without an issue source |
| 25 | |
| 26 | ## Platform-Specific Issue States |
| 27 | |
| 28 | Each platform tracks issue lifecycle differently. Squad normalizes these into a common board state. |
| 29 | |
| 30 | ### GitHub |
| 31 | |
| 32 | | GitHub State | GitHub API Fields | Squad Board State | |
| 33 | |--------------|-------------------|-------------------| |
| 34 | | Open, no assignee | `state: open`, `assignee: null` | `untriaged` | |
| 35 | | Open, assigned, no branch | `state: open`, `assignee: @user`, no linked PR | `assigned` | |
| 36 | | Open, branch exists | `state: open`, linked branch exists | `inProgress` | |
| 37 | | Open, PR opened | `state: open`, PR exists, `reviewDecision: null` | `needsReview` | |
| 38 | | Open, PR approved | `state: open`, PR `reviewDecision: APPROVED` | `readyToMerge` | |
| 39 | | Open, changes requested | `state: open`, PR `reviewDecision: CHANGES_REQUESTED` | `changesRequested` | |
| 40 | | Open, CI failure | `state: open`, PR `statusCheckRollup: FAILURE` | `ciFailure` | |
| 41 | | Closed | `state: closed` | `done` | |
| 42 | |
| 43 | **Issue labels used by Squad:** |
| 44 | - `squad` — Issue is in Squad backlog |
| 45 | - `squad:{member}` — Assigned to specific agent |
| 46 | - `squad:untriaged` — Needs triage |
| 47 | - `go:needs-research` — Needs investigation before implementation |
| 48 | - `priority:p{N}` — Priority level (0=critical, 1=high, 2=medium, 3=low) |
| 49 | - `next-up` — Queued for next agent pickup |
| 50 | |
| 51 | **Branch naming convention:** |
| 52 | ``` |
| 53 | squad/{issue-number}-{kebab-case-slug} |
| 54 | ``` |
| 55 | Example: `squad/42-fix-login-validation` |
| 56 | |
| 57 | ### Azure DevOps |
| 58 | |
| 59 | | ADO State | Squad Board State | |
| 60 | |-----------|-------------------| |
| 61 | | New | `untriaged` | |
| 62 | | Active, no branch | `assigned` | |
| 63 | | Active, branch exists | `inProgress` | |
| 64 | | Active, PR opened | `needsReview` | |
| 65 | | Active, PR approved | `readyToMerge` | |
| 66 | | Resolved | `done` | |
| 67 | | Closed | `done` | |
| 68 | |
| 69 | **Work item tags used by Squad:** |
| 70 | - `squad` — Work item is in Squad backlog |
| 71 | - `squad:{member}` — Assigned to specific agent |
| 72 | |
| 73 | **Branch naming convention:** |
| 74 | ``` |
| 75 | squad/{work-item-id}-{kebab-case-slug} |
| 76 | ``` |
| 77 | Example: `squad/1234-add-auth-module` |
| 78 | |
| 79 | ### Microsoft Planner |
| 80 | |
| 81 | Planner does not have native Git integration. Squad uses Planner for task tracking and GitHub/ADO for code management. |
| 82 | |
| 83 | | Planner Status | Squad Board State | |
| 84 | |----------------|-------------------| |
| 85 | | Not Started | `untriaged` | |
| 86 | | In Progress, no PR | `inProgress` | |
| 87 | | In Progress, PR opened | `needsReview` | |
| 88 | | Completed | `done` | |
| 89 | |
| 90 | **Planner→Git workflow:** |
| 91 | 1. Task created in Planner bucket |
| 92 | 2. Agent reads task from Planner |
| 93 | 3. Agent creates branch in GitHub/ADO repo |
| 94 | 4. Agent opens PR referencing Planner task ID in description |
| 95 | 5. Agent marks task as "Completed" when PR merges |
| 96 | |
| 97 | ## Issue → Branch → PR → Merge Lifecycle |
| 98 | |
| 99 | ### 1. Issue Assignment (Triage) |
| 100 | |
| 101 | **Trigger:** Ralph detects an untriaged issue or user manually assigns work. |
| 102 | |
| 103 | **Actions:** |
| 104 | 1. Read `.squad/routing.md` to determine which agent should handle the issue |
| 105 | 2. Apply `squad:{member}` label (GitHub) or tag (ADO) |
| 106 | 3. Transition issue to `assigned` state |
| 107 | 4. Optionally spawn agent immediately if issue is high-priority |
| 108 | |
| 109 | **Issue read command:** |
| 110 | ```bash |
| 111 | # GitHub |
| 112 | gh issue view {number} --json number,title,body,labels,assignees |
| 113 | |
| 114 | # Azure DevOps |
| 115 | az boards work-item show --id {id} --output json |
| 116 | ``` |
| 117 | |
| 118 | ### 2. Branch Creation (Start Work) |
| 119 | |
| 120 | **Trigger:** Agent accepts issue assignment and begins work. |
| 121 | |
| 122 | **Actions:** |
| 123 | 1. Ensure working on latest base branch (usually `main` or `dev`) |
| 124 | 2. Create feature branch using Squad naming convention |
| 125 | 3. Transition issue to `inProgress` state |
| 126 | |
| 127 | **Branch creation commands:** |
| 128 | |
| 129 | **Standard (single-agent, no parallelism):** |
| 130 | ```bash |
| 131 | git checkout main && git pull && git checkout -b squad/{issue-number}-{slug} |
| 132 | ``` |
| 133 | |
| 134 | **Worktree (parallel multi-agent):** |
| 135 | ```bash |
| 136 | git worktree add ../worktrees/{issue-number} -b squad/{issue-number}-{slug} |
| 137 | cd ../worktrees/{issue-number} |
| 138 | ``` |
| 139 | |
| 140 | > **Note:** Worktree support is in progress (#525). Current implementation uses standard checkout. |
| 141 | |
| 142 | ### 3. Implementation & Commit |
| 143 | |
| 144 | **Actions:** |
| 145 | 1. Agent makes code changes |
| 146 | 2. Commits reference the issue number |
| 147 | 3. Pushes branch to remote |
| 148 | |
| 149 | **Commit message format:** |
| 150 | ``` |
| 151 | {type}({scope}): {description} (#{issue-number}) |
| 152 | |
| 153 | {detailed explanation if needed} |
| 154 | |
| 155 | {breaking change notice if applicable} |
| 156 | |
| 157 | Closes #{issue-number} |
| 158 | |
| 159 | Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> |
| 160 | ``` |
| 161 | |
| 162 | **Commit types:** `feat`, `fix`, `docs`, `refactor`, `test`, `chore`, `perf`, `style`, `build`, `ci` |
| 163 | |
| 164 | **Push command:** |
| 165 | ```bash |
| 166 | git push -u origin squad/{issue-number}-{slug} |
| 167 | ``` |
| 168 | |
| 169 | ### 4. PR Creation |
| 170 | |
| 171 | **Trigger:** Agent completes implementation and is ready for review. |
| 172 | |
| 173 | **Actions:** |
| 174 | 1. Open PR from feature branch to base branch |
| 175 | 2. Reference issue in PR description |
| 176 | 3. Apply labels if needed |
| 177 | 4. Transition issue to `needsReview` state |
| 178 | |
| 179 | **PR creation commands:** |
| 180 | |
| 181 | **GitHub:** |
| 182 | ```bash |
| 183 | gh pr create --title "{title}" \ |
| 184 | --body "Closes #{issue-number}\n\n{description}" \ |
| 185 | --head squad/{issue-number}-{slug} \ |
| 186 | --base main |
| 187 | ``` |
| 188 | |
| 189 | **Azure DevOps:** |
| 190 | ```bash |
| 191 | az repos pr create --title "{title}" \ |
| 192 | --description "Closes #{work-item-id}\n\n{description}" \ |
| 193 | --source-branch squad/{work-item-id}-{slug} \ |
| 194 | --target-branch main |
| 195 | ``` |
| 196 | |
| 197 | **PR description template:** |
| 198 | ```markdown |
| 199 | Closes #{issue-number} |
| 200 | |
| 201 | ## Summary |
| 202 | {what changed} |
| 203 | |
| 204 | ## Changes |
| 205 | - {change 1} |
| 206 | - {change 2} |
| 207 | |
| 208 | ## Testing |
| 209 | {how this was tested} |
| 210 | |
| 211 | {If working as a squad member:} |
| 212 | Working as {member} ({role}) |
| 213 | |
| 214 | {If needs human review:} |
| 215 | ⚠️ This task was flagged as "needs review" — please have a squad member review before merging. |
| 216 | ``` |
| 217 | |
| 218 | ### 5. PR Review & Updates |
| 219 | |
| 220 | **Review states:** |
| 221 | - **Approved** → `readyToMerge` |
| 222 | - **Changes requested** → `changesRequested` |
| 223 | - **CI failure** → `ciFailure` |
| 224 | |
| 225 | **When changes are requested:** |
| 226 | 1. Agent addresses feedback |
| 227 | 2. Commits fixes to the same branch |
| 228 | 3. Pushes updates |
| 229 | 4. Requests re-review |
| 230 | |
| 231 | **Update workflow:** |
| 232 | ```bash |
| 233 | # Make changes |
| 234 | # ⚠️ NEVER use `git add .` or `git add -A` — only stage files you intentionally changed |
| 235 | git add -- {specific files you modified} |
| 236 | git commit -m "fix: address review feedback" |
| 237 | git push |
| 238 | ``` |
| 239 | |
| 240 | **Re-request review (GitHub):** |
| 241 | ```bash |
| 242 | gh pr ready {pr-number} |
| 243 | ``` |
| 244 | |
| 245 | ### 6. PR Merge |
| 246 | |
| 247 | **Trigger:** PR is approved and CI passes. |
| 248 | |
| 249 | **Merge strategies:** |
| 250 | |
| 251 | **GitHub (merge commit):** |
| 252 | ```bash |
| 253 | gh pr merge {pr-number} --merge --delete-branch |
| 254 | ``` |
| 255 | |
| 256 | **GitHub (squash):** |
| 257 | ```bash |
| 258 | gh pr merge {pr-number} --squash --delete-branch |
| 259 | ``` |
| 260 | |
| 261 | **Azure DevOps:** |
| 262 | ```bash |
| 263 | az repos pr update --id {pr-id} --status completed --delete-source-branch true |
| 264 | ``` |
| 265 | |
| 266 | **Post-merge actions:** |
| 267 | 1. Issue automatically closes (if "Closes #{number}" is in PR description) |
| 268 | 2. Feature branch is deleted |
| 269 | 3. Squad board state transitions to `done` |
| 270 | 4. Worktree cleanup (if worktree was used — #525) |
| 271 | |
| 272 | ### 7. Cleanup |
| 273 | |
| 274 | **Standard workflow cleanup:** |
| 275 | ```bash |
| 276 | git checkout main |
| 277 | git pull |
| 278 | git branch -d squad/{issue-number}-{slug} |
| 279 | ``` |
| 280 | |
| 281 | **Worktree cleanup (future, #525):** |
| 282 | ```bash |
| 283 | cd {original-cwd} |
| 284 | git worktree remove ../worktrees/{issue-number} |
| 285 | ``` |
| 286 | |
| 287 | ## Spawn Prompt Additions for Issue Work |
| 288 | |
| 289 | When spawning an agent to work on an issue, include this context block: |
| 290 | |
| 291 | ```markdown |
| 292 | ## ISSUE CONTEXT |
| 293 | |
| 294 | **Issue:** #{number} — {title} |
| 295 | **Platform:** {GitHub | Azure DevOps | Planner} |
| 296 | **Repository:** {owner}/{repo} |
| 297 | **Assigned to:** {member} |
| 298 | |
| 299 | **Description:** |
| 300 | {issue body} |
| 301 | |
| 302 | **Labels/Tags:** |
| 303 | {labels} |
| 304 | |
| 305 | **Acceptance Criteria:** |
| 306 | {criteria if present in issue} |
| 307 | |
| 308 | **Branch:** `squad/{issue-number}-{slug}` |
| 309 | |
| 310 | **Your task:** |
| 311 | {specific directive to the agent} |
| 312 | |
| 313 | **After completing work:** |
| 314 | 1. Commit with message referencing issue number |
| 315 | 2. Push branch |
| 316 | 3. Open PR using: |
| 317 | ``` |
| 318 | gh pr create --title "{title}" --body "Closes #{number}\n\n{description}" --head squad/{issue-number}-{slug} --base {base-branch} |
| 319 | ``` |
| 320 | 4. Report PR URL to coordinator |
| 321 | ``` |
| 322 | |
| 323 | ## Ralph's Role in Issue Lifecycle |
| 324 | |
| 325 | Ralph (the work monitor) continuously checks issue and PR state: |
| 326 | |
| 327 | 1. **Triage:** Detects untriaged issues, assigns `squad:{member}` labels |
| 328 | 2. **Spawn:** Launches agents for assigned issues |
| 329 | 3. **Monitor:** Tracks PR state transitions (needsReview → changesRequested → readyToMerge) |
| 330 | 4. **Merge:** Automatically merges approved PRs |
| 331 | 5. **Cleanup:** Marks issues as done when PRs merge |
| 332 | |
| 333 | **Ralph's work-check cycle:** |
| 334 | ``` |
| 335 | Scan → Categorize → Dispatch → Watch → Report → Loop |
| 336 | ``` |
| 337 | |
| 338 | See `.squad/templates/ralph-reference.md` for Ralph's full lifecycle. |
| 339 | |
| 340 | ## PR Review Handling |
| 341 | |
| 342 | ### Automated Approval (CI-only projects) |
| 343 | |
| 344 | If the project has no human reviewers configured: |
| 345 | 1. PR opens |
| 346 | 2. CI runs |
| 347 | 3. If CI passes, Ralph auto-merges |
| 348 | 4. Issue closes |
| 349 | |
| 350 | ### Human Review Required |
| 351 | |
| 352 | If the project requires human approval: |
| 353 | 1. PR opens |
| 354 | 2. Human reviewer is notified (GitHub/ADO notifications) |
| 355 | 3. Reviewer approves or requests changes |
| 356 | 4. If approved + CI passes, Ralph merges |
| 357 | 5. If changes requested, agent addresses feedback |
| 358 | |
| 359 | ### Squad Member Review |
| 360 | |
| 361 | If the issue was assigned to a squad member and they authored the PR: |
| 362 | 1. Another squad member reviews (conflict of interest avoidance) |
| 363 | 2. Original author is locked out from re-working rejected code (rejection lockout) |
| 364 | 3. Reviewer can approve edits or reject outright |
| 365 | |
| 366 | ## Common Issue Lifecycle Patterns |
| 367 | |
| 368 | ### Pattern 1: Quick Fix (Single Agent, No Review) |
| 369 | ``` |
| 370 | Issue created → Assigned to agent → Branch created → Code fixed → |
| 371 | PR opened → CI passes → Auto-merged → Issue closed |
| 372 | ``` |
| 373 | |
| 374 | ### Pattern 2: Feature Development (Human Review) |
| 375 | ``` |
| 376 | Issue created → Assigned to agent → Branch created → Feature implemented → |
| 377 | PR opened → Human reviews → Changes requested → Agent fixes → |
| 378 | Re-reviewed → Approved → Merged → Issue closed |
| 379 | ``` |
| 380 | |
| 381 | ### Pattern 3: Research-Then-Implement |
| 382 | ``` |
| 383 | Issue created → Labeled `go:needs-research` → Research agent spawned → |
| 384 | Research documented → Research PR merged → Implementation issue created → |
| 385 | Implementation agent spawned → Feature built → PR merged |
| 386 | ``` |
| 387 | |
| 388 | ### Pattern 4: Parallel Multi-Agent (Future, #525) |
| 389 | ``` |
| 390 | Epic issue created → Decomposed into sub-issues → Each sub-issue assigned → |
| 391 | Multiple agents work in parallel worktrees → PRs opened concurrently → |
| 392 | All PRs reviewed → All PRs merged → Epic closed |
| 393 | ``` |
| 394 | |
| 395 | ## Anti-Patterns |
| 396 | |
| 397 | - ❌ Creating branches without linking to an issue |
| 398 | - ❌ Committing without issue reference in message |
| 399 | - ❌ Opening PRs without "Closes #{number}" in description |
| 400 | - ❌ Merging PRs before CI passes |
| 401 | - ❌ Leaving feature branches undeleted after merge |
| 402 | - ❌ Using `checkout -b` when parallel agents are active (causes working directory conflicts) |
| 403 | - ❌ Manually transitioning issue states — let the platform and Squad automation handle it |
| 404 | - ❌ Skipping the branch naming convention — breaks Ralph's tracking logic |
| 405 | |
| 406 | ## Migration Notes |
| 407 | |
| 408 | **v0.8.x → v0.9.x (Worktree Support):** |
| 409 | - `checkout -b` → `git worktree add` for parallel agents |
| 410 | - Worktree cleanup added to post-merge flow |
| 411 | - `TEAM_ROOT` passing to agents to support worktree-aware state resolution |
| 412 | |
| 413 | This template will be updated as worktree lifecycle support lands in #525. |