@bradygaster/squad-cli 0.8.25 → 0.9.1
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.
- package/README.md +329 -77
- package/dist/cli/commands/aspire.d.ts.map +1 -1
- package/dist/cli/commands/aspire.js +3 -0
- package/dist/cli/commands/aspire.js.map +1 -1
- package/dist/cli/commands/build.js +3 -3
- package/dist/cli/commands/build.js.map +1 -1
- package/dist/cli/commands/cast.d.ts +13 -0
- package/dist/cli/commands/cast.d.ts.map +1 -0
- package/dist/cli/commands/cast.js +77 -0
- package/dist/cli/commands/cast.js.map +1 -0
- package/dist/cli/commands/cost.d.ts +2 -0
- package/dist/cli/commands/cost.d.ts.map +1 -0
- package/dist/cli/commands/cost.js +170 -0
- package/dist/cli/commands/cost.js.map +1 -0
- package/dist/cli/commands/cross-squad.d.ts +12 -0
- package/dist/cli/commands/cross-squad.d.ts.map +1 -0
- package/dist/cli/commands/cross-squad.js +80 -0
- package/dist/cli/commands/cross-squad.js.map +1 -0
- package/dist/cli/commands/doctor.d.ts +5 -0
- package/dist/cli/commands/doctor.d.ts.map +1 -1
- package/dist/cli/commands/doctor.js +156 -0
- package/dist/cli/commands/doctor.js.map +1 -1
- package/dist/cli/commands/economy.d.ts +10 -0
- package/dist/cli/commands/economy.d.ts.map +1 -0
- package/dist/cli/commands/economy.js +64 -0
- package/dist/cli/commands/economy.js.map +1 -0
- package/dist/cli/commands/export.d.ts.map +1 -1
- package/dist/cli/commands/export.js +11 -4
- package/dist/cli/commands/export.js.map +1 -1
- package/dist/cli/commands/import.js +2 -2
- package/dist/cli/commands/import.js.map +1 -1
- package/dist/cli/commands/personal.d.ts +16 -0
- package/dist/cli/commands/personal.d.ts.map +1 -0
- package/dist/cli/commands/personal.js +213 -0
- package/dist/cli/commands/personal.js.map +1 -0
- package/dist/cli/commands/roles.d.ts +2 -0
- package/dist/cli/commands/roles.d.ts.map +1 -0
- package/dist/cli/commands/roles.js +54 -0
- package/dist/cli/commands/roles.js.map +1 -0
- package/dist/cli/commands/schedule.d.ts +14 -0
- package/dist/cli/commands/schedule.d.ts.map +1 -0
- package/dist/cli/commands/schedule.js +208 -0
- package/dist/cli/commands/schedule.js.map +1 -0
- package/dist/cli/commands/watch.d.ts.map +1 -1
- package/dist/cli/commands/watch.js +17 -5
- package/dist/cli/commands/watch.js.map +1 -1
- package/dist/cli/core/cast.d.ts +9 -0
- package/dist/cli/core/cast.d.ts.map +1 -1
- package/dist/cli/core/cast.js +170 -60
- package/dist/cli/core/cast.js.map +1 -1
- package/dist/cli/core/detect-squad-dir.d.ts +10 -0
- package/dist/cli/core/detect-squad-dir.d.ts.map +1 -1
- package/dist/cli/core/detect-squad-dir.js +47 -0
- package/dist/cli/core/detect-squad-dir.js.map +1 -1
- package/dist/cli/core/init.d.ts +8 -0
- package/dist/cli/core/init.d.ts.map +1 -1
- package/dist/cli/core/init.js +115 -2
- package/dist/cli/core/init.js.map +1 -1
- package/dist/cli/core/migrations.d.ts.map +1 -1
- package/dist/cli/core/migrations.js +21 -0
- package/dist/cli/core/migrations.js.map +1 -1
- package/dist/cli/core/team-md.js +34 -34
- package/dist/cli/core/templates.d.ts.map +1 -1
- package/dist/cli/core/templates.js +8 -1
- package/dist/cli/core/templates.js.map +1 -1
- package/dist/cli/core/upgrade.d.ts +14 -0
- package/dist/cli/core/upgrade.d.ts.map +1 -1
- package/dist/cli/core/upgrade.js +182 -48
- package/dist/cli/core/upgrade.js.map +1 -1
- package/dist/cli/core/version.js +2 -2
- package/dist/cli/core/version.js.map +1 -1
- package/dist/cli/index.d.ts +2 -0
- package/dist/cli/index.d.ts.map +1 -1
- package/dist/cli/index.js +2 -0
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/self-update.d.ts +21 -0
- package/dist/cli/self-update.d.ts.map +1 -0
- package/dist/cli/self-update.js +113 -0
- package/dist/cli/self-update.js.map +1 -0
- package/dist/cli/shell/autocomplete.d.ts.map +1 -1
- package/dist/cli/shell/autocomplete.js +5 -0
- package/dist/cli/shell/autocomplete.js.map +1 -1
- package/dist/cli/shell/commands.d.ts.map +1 -1
- package/dist/cli/shell/commands.js +55 -24
- package/dist/cli/shell/commands.js.map +1 -1
- package/dist/cli/shell/components/AgentPanel.d.ts.map +1 -1
- package/dist/cli/shell/components/AgentPanel.js +21 -6
- package/dist/cli/shell/components/AgentPanel.js.map +1 -1
- package/dist/cli/shell/components/App.d.ts.map +1 -1
- package/dist/cli/shell/components/App.js +33 -15
- package/dist/cli/shell/components/App.js.map +1 -1
- package/dist/cli/shell/components/InputPrompt.js +1 -1
- package/dist/cli/shell/components/InputPrompt.js.map +1 -1
- package/dist/cli/shell/components/MessageStream.d.ts +2 -0
- package/dist/cli/shell/components/MessageStream.d.ts.map +1 -1
- package/dist/cli/shell/components/MessageStream.js +20 -20
- package/dist/cli/shell/components/MessageStream.js.map +1 -1
- package/dist/cli/shell/components/ThinkingIndicator.d.ts +4 -0
- package/dist/cli/shell/components/ThinkingIndicator.d.ts.map +1 -1
- package/dist/cli/shell/components/ThinkingIndicator.js +23 -4
- package/dist/cli/shell/components/ThinkingIndicator.js.map +1 -1
- package/dist/cli/shell/coordinator.d.ts +7 -0
- package/dist/cli/shell/coordinator.d.ts.map +1 -1
- package/dist/cli/shell/coordinator.js +206 -88
- package/dist/cli/shell/coordinator.js.map +1 -1
- package/dist/cli/shell/error-messages.d.ts +14 -0
- package/dist/cli/shell/error-messages.d.ts.map +1 -1
- package/dist/cli/shell/error-messages.js +65 -1
- package/dist/cli/shell/error-messages.js.map +1 -1
- package/dist/cli/shell/index.d.ts +1 -1
- package/dist/cli/shell/index.d.ts.map +1 -1
- package/dist/cli/shell/index.js +83 -12
- package/dist/cli/shell/index.js.map +1 -1
- package/dist/cli/shell/router.d.ts.map +1 -1
- package/dist/cli/shell/router.js +21 -2
- package/dist/cli/shell/router.js.map +1 -1
- package/dist/cli/shell/stream-bridge.d.ts +2 -0
- package/dist/cli/shell/stream-bridge.d.ts.map +1 -1
- package/dist/cli/shell/stream-bridge.js +11 -2
- package/dist/cli/shell/stream-bridge.js.map +1 -1
- package/dist/cli/shell/terminal.d.ts +5 -5
- package/dist/cli/shell/terminal.d.ts.map +1 -1
- package/dist/cli/shell/terminal.js +35 -26
- package/dist/cli/shell/terminal.js.map +1 -1
- package/dist/cli-entry.js +124 -42
- package/dist/cli-entry.js.map +1 -1
- package/package.json +20 -4
- package/scripts/patch-esm-imports.mjs +106 -77
- package/scripts/patch-ink-rendering.mjs +115 -0
- package/templates/casting/Futurama.json +10 -0
- package/templates/casting-history.json +4 -4
- package/templates/casting-policy.json +37 -35
- package/templates/casting-reference.md +104 -0
- package/templates/casting-registry.json +3 -3
- package/templates/ceremonies.md +41 -41
- package/templates/charter.md +53 -53
- package/templates/constraint-tracking.md +38 -38
- package/templates/cooperative-rate-limiting.md +229 -0
- package/templates/copilot-instructions.md +46 -46
- package/templates/history.md +10 -10
- package/templates/identity/now.md +9 -9
- package/templates/identity/wisdom.md +15 -15
- package/templates/issue-lifecycle.md +412 -0
- package/templates/keda-scaler.md +164 -0
- package/templates/machine-capabilities.md +75 -0
- package/templates/mcp-config.md +90 -90
- package/templates/multi-agent-format.md +28 -28
- package/templates/orchestration-log.md +27 -27
- package/templates/plugin-marketplace.md +49 -49
- package/templates/ralph-circuit-breaker.md +313 -0
- package/templates/raw-agent-output.md +37 -37
- package/templates/roster.md +60 -60
- package/templates/routing.md +39 -54
- package/templates/run-output.md +50 -50
- package/templates/scribe-charter.md +119 -119
- package/templates/skill.md +24 -24
- package/templates/skills/agent-collaboration/SKILL.md +42 -0
- package/templates/skills/agent-conduct/SKILL.md +24 -0
- package/templates/skills/architectural-proposals/SKILL.md +151 -0
- package/templates/skills/ci-validation-gates/SKILL.md +84 -0
- package/templates/skills/cli-wiring/SKILL.md +47 -0
- package/templates/skills/client-compatibility/SKILL.md +89 -0
- package/templates/skills/cross-squad/SKILL.md +114 -0
- package/templates/skills/distributed-mesh/SKILL.md +287 -0
- package/templates/skills/distributed-mesh/mesh.json.example +30 -0
- package/templates/skills/distributed-mesh/sync-mesh.ps1 +111 -0
- package/templates/skills/distributed-mesh/sync-mesh.sh +104 -0
- package/templates/skills/docs-standards/SKILL.md +71 -0
- package/templates/skills/economy-mode/SKILL.md +114 -0
- package/templates/skills/external-comms/SKILL.md +329 -0
- package/templates/skills/gh-auth-isolation/SKILL.md +183 -0
- package/templates/skills/git-workflow/SKILL.md +204 -0
- package/templates/skills/github-multi-account/SKILL.md +95 -0
- package/templates/skills/history-hygiene/SKILL.md +36 -0
- package/templates/skills/humanizer/SKILL.md +105 -0
- package/templates/skills/init-mode/SKILL.md +102 -0
- package/templates/skills/model-selection/SKILL.md +117 -0
- package/templates/skills/nap/SKILL.md +24 -0
- package/templates/skills/personal-squad/SKILL.md +57 -0
- package/templates/skills/release-process/SKILL.md +423 -0
- package/templates/skills/reskill/SKILL.md +92 -0
- package/templates/skills/reviewer-protocol/SKILL.md +79 -0
- package/templates/skills/secret-handling/SKILL.md +200 -0
- package/templates/skills/session-recovery/SKILL.md +155 -0
- package/templates/skills/squad-conventions/SKILL.md +69 -69
- package/templates/skills/test-discipline/SKILL.md +37 -0
- package/templates/skills/windows-compatibility/SKILL.md +74 -0
- package/templates/squad.agent.md +1287 -1146
- package/templates/workflows/squad-ci.yml +24 -24
- package/templates/workflows/squad-docs.yml +54 -50
- package/templates/workflows/squad-heartbeat.yml +3 -4
- package/templates/workflows/squad-insider-release.yml +61 -61
- package/templates/workflows/squad-issue-assign.yml +161 -161
- package/templates/workflows/squad-label-enforce.yml +181 -181
- package/templates/workflows/squad-preview.yml +55 -55
- package/templates/workflows/squad-promote.yml +120 -120
- package/templates/workflows/squad-release.yml +77 -77
- package/templates/workflows/squad-triage.yml +260 -260
- package/templates/workflows/sync-squad-labels.yml +169 -169
|
@@ -0,0 +1,313 @@
|
|
|
1
|
+
# Ralph Circuit Breaker — Model Rate Limit Fallback
|
|
2
|
+
|
|
3
|
+
> Classic circuit breaker pattern (Hystrix / Polly / Resilience4j) applied to Copilot model selection.
|
|
4
|
+
> When the preferred model hits rate limits, Ralph automatically degrades to free-tier models, then self-heals.
|
|
5
|
+
|
|
6
|
+
## Problem
|
|
7
|
+
|
|
8
|
+
When running multiple Ralph instances across repos, Copilot model rate limits cause cascading failures.
|
|
9
|
+
All Ralphs fail simultaneously when the preferred model (e.g., `claude-sonnet-4.6`) hits quota.
|
|
10
|
+
|
|
11
|
+
Premium models burn quota fast:
|
|
12
|
+
| Model | Multiplier | Risk |
|
|
13
|
+
|-------|-----------|------|
|
|
14
|
+
| `claude-sonnet-4.6` | 1x | Moderate with many Ralphs |
|
|
15
|
+
| `claude-opus-4.6` | 10x | High |
|
|
16
|
+
| `gpt-5.4` | 50x | Very high |
|
|
17
|
+
| `gpt-5.4-mini` | **0x** | **Free — unlimited** |
|
|
18
|
+
| `gpt-5-mini` | **0x** | **Free — unlimited** |
|
|
19
|
+
| `gpt-4.1` | **0x** | **Free — unlimited** |
|
|
20
|
+
|
|
21
|
+
## Circuit Breaker States
|
|
22
|
+
|
|
23
|
+
```
|
|
24
|
+
┌─────────┐ rate limit error ┌────────┐
|
|
25
|
+
│ CLOSED │ ───────────────────► │ OPEN │
|
|
26
|
+
│ (normal)│ │(fallback)│
|
|
27
|
+
└────┬────┘ ◄──────────────── └────┬────┘
|
|
28
|
+
│ 2 consecutive │
|
|
29
|
+
│ successes │ cooldown expires
|
|
30
|
+
│ ▼
|
|
31
|
+
│ ┌──────────┐
|
|
32
|
+
└───── success ◄──────── │HALF-OPEN │
|
|
33
|
+
(close) │ (testing) │
|
|
34
|
+
└──────────┘
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
### CLOSED (normal operation)
|
|
38
|
+
- Use preferred model from config
|
|
39
|
+
- Every successful response confirms circuit stays closed
|
|
40
|
+
- On rate limit error → transition to OPEN
|
|
41
|
+
|
|
42
|
+
### OPEN (rate limited — fallback active)
|
|
43
|
+
- Fall back through the free-tier model chain:
|
|
44
|
+
1. `gpt-5.4-mini`
|
|
45
|
+
2. `gpt-5-mini`
|
|
46
|
+
3. `gpt-4.1`
|
|
47
|
+
- Start cooldown timer (default: 10 minutes)
|
|
48
|
+
- When cooldown expires → transition to HALF-OPEN
|
|
49
|
+
|
|
50
|
+
### HALF-OPEN (testing recovery)
|
|
51
|
+
- Try preferred model again
|
|
52
|
+
- If 2 consecutive successes → transition to CLOSED
|
|
53
|
+
- If rate limit error → back to OPEN, reset cooldown
|
|
54
|
+
|
|
55
|
+
## State File: `.squad/ralph-circuit-breaker.json`
|
|
56
|
+
|
|
57
|
+
```json
|
|
58
|
+
{
|
|
59
|
+
"state": "closed",
|
|
60
|
+
"preferredModel": "claude-sonnet-4.6",
|
|
61
|
+
"fallbackChain": ["gpt-5.4-mini", "gpt-5-mini", "gpt-4.1"],
|
|
62
|
+
"currentFallbackIndex": 0,
|
|
63
|
+
"cooldownMinutes": 10,
|
|
64
|
+
"openedAt": null,
|
|
65
|
+
"halfOpenSuccesses": 0,
|
|
66
|
+
"consecutiveFailures": 0,
|
|
67
|
+
"metrics": {
|
|
68
|
+
"totalFallbacks": 0,
|
|
69
|
+
"totalRecoveries": 0,
|
|
70
|
+
"lastFallbackAt": null,
|
|
71
|
+
"lastRecoveryAt": null
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
## PowerShell Functions
|
|
77
|
+
|
|
78
|
+
Paste these into your `ralph-watch.ps1` or source them from a shared module.
|
|
79
|
+
|
|
80
|
+
### `Get-CircuitBreakerState`
|
|
81
|
+
|
|
82
|
+
```powershell
|
|
83
|
+
function Get-CircuitBreakerState {
|
|
84
|
+
param([string]$StateFile = ".squad/ralph-circuit-breaker.json")
|
|
85
|
+
|
|
86
|
+
if (-not (Test-Path $StateFile)) {
|
|
87
|
+
$default = @{
|
|
88
|
+
state = "closed"
|
|
89
|
+
preferredModel = "claude-sonnet-4.6"
|
|
90
|
+
fallbackChain = @("gpt-5.4-mini", "gpt-5-mini", "gpt-4.1")
|
|
91
|
+
currentFallbackIndex = 0
|
|
92
|
+
cooldownMinutes = 10
|
|
93
|
+
openedAt = $null
|
|
94
|
+
halfOpenSuccesses = 0
|
|
95
|
+
consecutiveFailures = 0
|
|
96
|
+
metrics = @{
|
|
97
|
+
totalFallbacks = 0
|
|
98
|
+
totalRecoveries = 0
|
|
99
|
+
lastFallbackAt = $null
|
|
100
|
+
lastRecoveryAt = $null
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
$default | ConvertTo-Json -Depth 3 | Set-Content $StateFile
|
|
104
|
+
return $default
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
return (Get-Content $StateFile -Raw | ConvertFrom-Json)
|
|
108
|
+
}
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
### `Save-CircuitBreakerState`
|
|
112
|
+
|
|
113
|
+
```powershell
|
|
114
|
+
function Save-CircuitBreakerState {
|
|
115
|
+
param(
|
|
116
|
+
[object]$State,
|
|
117
|
+
[string]$StateFile = ".squad/ralph-circuit-breaker.json"
|
|
118
|
+
)
|
|
119
|
+
|
|
120
|
+
$State | ConvertTo-Json -Depth 3 | Set-Content $StateFile
|
|
121
|
+
}
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
### `Get-CurrentModel`
|
|
125
|
+
|
|
126
|
+
Returns the model Ralph should use right now, based on circuit state.
|
|
127
|
+
|
|
128
|
+
```powershell
|
|
129
|
+
function Get-CurrentModel {
|
|
130
|
+
param([string]$StateFile = ".squad/ralph-circuit-breaker.json")
|
|
131
|
+
|
|
132
|
+
$cb = Get-CircuitBreakerState -StateFile $StateFile
|
|
133
|
+
|
|
134
|
+
switch ($cb.state) {
|
|
135
|
+
"closed" {
|
|
136
|
+
return $cb.preferredModel
|
|
137
|
+
}
|
|
138
|
+
"open" {
|
|
139
|
+
# Check if cooldown has expired
|
|
140
|
+
if ($cb.openedAt) {
|
|
141
|
+
$opened = [DateTime]::Parse($cb.openedAt)
|
|
142
|
+
$elapsed = (Get-Date) - $opened
|
|
143
|
+
if ($elapsed.TotalMinutes -ge $cb.cooldownMinutes) {
|
|
144
|
+
# Transition to half-open
|
|
145
|
+
$cb.state = "half-open"
|
|
146
|
+
$cb.halfOpenSuccesses = 0
|
|
147
|
+
Save-CircuitBreakerState -State $cb -StateFile $StateFile
|
|
148
|
+
Write-Host " [circuit-breaker] Cooldown expired. Testing preferred model..." -ForegroundColor Yellow
|
|
149
|
+
return $cb.preferredModel
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
# Still in cooldown — use fallback
|
|
153
|
+
$idx = [Math]::Min($cb.currentFallbackIndex, $cb.fallbackChain.Count - 1)
|
|
154
|
+
return $cb.fallbackChain[$idx]
|
|
155
|
+
}
|
|
156
|
+
"half-open" {
|
|
157
|
+
return $cb.preferredModel
|
|
158
|
+
}
|
|
159
|
+
default {
|
|
160
|
+
return $cb.preferredModel
|
|
161
|
+
}
|
|
162
|
+
}
|
|
163
|
+
}
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
### `Update-CircuitBreakerOnSuccess`
|
|
167
|
+
|
|
168
|
+
Call after every successful model response.
|
|
169
|
+
|
|
170
|
+
```powershell
|
|
171
|
+
function Update-CircuitBreakerOnSuccess {
|
|
172
|
+
param([string]$StateFile = ".squad/ralph-circuit-breaker.json")
|
|
173
|
+
|
|
174
|
+
$cb = Get-CircuitBreakerState -StateFile $StateFile
|
|
175
|
+
$cb.consecutiveFailures = 0
|
|
176
|
+
|
|
177
|
+
if ($cb.state -eq "half-open") {
|
|
178
|
+
$cb.halfOpenSuccesses++
|
|
179
|
+
if ($cb.halfOpenSuccesses -ge 2) {
|
|
180
|
+
# Recovery! Close the circuit
|
|
181
|
+
$cb.state = "closed"
|
|
182
|
+
$cb.openedAt = $null
|
|
183
|
+
$cb.halfOpenSuccesses = 0
|
|
184
|
+
$cb.currentFallbackIndex = 0
|
|
185
|
+
$cb.metrics.totalRecoveries++
|
|
186
|
+
$cb.metrics.lastRecoveryAt = (Get-Date).ToString("o")
|
|
187
|
+
Save-CircuitBreakerState -State $cb -StateFile $StateFile
|
|
188
|
+
Write-Host " [circuit-breaker] RECOVERED — back to preferred model ($($cb.preferredModel))" -ForegroundColor Green
|
|
189
|
+
return
|
|
190
|
+
}
|
|
191
|
+
Save-CircuitBreakerState -State $cb -StateFile $StateFile
|
|
192
|
+
Write-Host " [circuit-breaker] Half-open success $($cb.halfOpenSuccesses)/2" -ForegroundColor Yellow
|
|
193
|
+
return
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
# closed state — nothing to do
|
|
197
|
+
}
|
|
198
|
+
```
|
|
199
|
+
|
|
200
|
+
### `Update-CircuitBreakerOnRateLimit`
|
|
201
|
+
|
|
202
|
+
Call when a model response indicates rate limiting (HTTP 429 or error message containing "rate limit").
|
|
203
|
+
|
|
204
|
+
```powershell
|
|
205
|
+
function Update-CircuitBreakerOnRateLimit {
|
|
206
|
+
param([string]$StateFile = ".squad/ralph-circuit-breaker.json")
|
|
207
|
+
|
|
208
|
+
$cb = Get-CircuitBreakerState -StateFile $StateFile
|
|
209
|
+
$cb.consecutiveFailures++
|
|
210
|
+
|
|
211
|
+
if ($cb.state -eq "closed" -or $cb.state -eq "half-open") {
|
|
212
|
+
# Open the circuit
|
|
213
|
+
$cb.state = "open"
|
|
214
|
+
$cb.openedAt = (Get-Date).ToString("o")
|
|
215
|
+
$cb.halfOpenSuccesses = 0
|
|
216
|
+
$cb.currentFallbackIndex = 0
|
|
217
|
+
$cb.metrics.totalFallbacks++
|
|
218
|
+
$cb.metrics.lastFallbackAt = (Get-Date).ToString("o")
|
|
219
|
+
Save-CircuitBreakerState -State $cb -StateFile $StateFile
|
|
220
|
+
|
|
221
|
+
$fallbackModel = $cb.fallbackChain[0]
|
|
222
|
+
Write-Host " [circuit-breaker] RATE LIMITED — falling back to $fallbackModel (cooldown: $($cb.cooldownMinutes)m)" -ForegroundColor Red
|
|
223
|
+
return
|
|
224
|
+
}
|
|
225
|
+
|
|
226
|
+
if ($cb.state -eq "open") {
|
|
227
|
+
# Already open — try next fallback in chain if current one also fails
|
|
228
|
+
if ($cb.currentFallbackIndex -lt ($cb.fallbackChain.Count - 1)) {
|
|
229
|
+
$cb.currentFallbackIndex++
|
|
230
|
+
$nextModel = $cb.fallbackChain[$cb.currentFallbackIndex]
|
|
231
|
+
Write-Host " [circuit-breaker] Fallback also limited — trying $nextModel" -ForegroundColor Red
|
|
232
|
+
}
|
|
233
|
+
# Reset cooldown timer
|
|
234
|
+
$cb.openedAt = (Get-Date).ToString("o")
|
|
235
|
+
Save-CircuitBreakerState -State $cb -StateFile $StateFile
|
|
236
|
+
}
|
|
237
|
+
}
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
## Integration with ralph-watch.ps1
|
|
241
|
+
|
|
242
|
+
In your Ralph polling loop, wrap the model selection:
|
|
243
|
+
|
|
244
|
+
```powershell
|
|
245
|
+
# At the top of your polling loop
|
|
246
|
+
$model = Get-CurrentModel
|
|
247
|
+
|
|
248
|
+
# When invoking copilot CLI
|
|
249
|
+
$result = copilot-cli --model $model ...
|
|
250
|
+
|
|
251
|
+
# After the call
|
|
252
|
+
if ($result -match "rate.?limit" -or $LASTEXITCODE -eq 429) {
|
|
253
|
+
Update-CircuitBreakerOnRateLimit
|
|
254
|
+
} else {
|
|
255
|
+
Update-CircuitBreakerOnSuccess
|
|
256
|
+
}
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
### Full integration example
|
|
260
|
+
|
|
261
|
+
```powershell
|
|
262
|
+
# Source the circuit breaker functions
|
|
263
|
+
. .squad-templates/ralph-circuit-breaker-functions.ps1
|
|
264
|
+
|
|
265
|
+
while ($true) {
|
|
266
|
+
$model = Get-CurrentModel
|
|
267
|
+
Write-Host "Polling with model: $model"
|
|
268
|
+
|
|
269
|
+
try {
|
|
270
|
+
# Your existing Ralph logic here, but pass $model
|
|
271
|
+
$response = Invoke-RalphCycle -Model $model
|
|
272
|
+
|
|
273
|
+
# Success path
|
|
274
|
+
Update-CircuitBreakerOnSuccess
|
|
275
|
+
}
|
|
276
|
+
catch {
|
|
277
|
+
if ($_.Exception.Message -match "rate.?limit|429|quota|Too Many Requests") {
|
|
278
|
+
Update-CircuitBreakerOnRateLimit
|
|
279
|
+
# Retry immediately with fallback model
|
|
280
|
+
continue
|
|
281
|
+
}
|
|
282
|
+
# Other errors — handle normally
|
|
283
|
+
throw
|
|
284
|
+
}
|
|
285
|
+
|
|
286
|
+
Start-Sleep -Seconds $pollInterval
|
|
287
|
+
}
|
|
288
|
+
```
|
|
289
|
+
|
|
290
|
+
## Configuration
|
|
291
|
+
|
|
292
|
+
Override defaults by editing `.squad/ralph-circuit-breaker.json`:
|
|
293
|
+
|
|
294
|
+
| Field | Default | Description |
|
|
295
|
+
|-------|---------|-------------|
|
|
296
|
+
| `preferredModel` | `claude-sonnet-4.6` | Model to use when circuit is closed |
|
|
297
|
+
| `fallbackChain` | `["gpt-5.4-mini", "gpt-5-mini", "gpt-4.1"]` | Ordered fallback models (all free-tier) |
|
|
298
|
+
| `cooldownMinutes` | `10` | How long to wait before testing recovery |
|
|
299
|
+
|
|
300
|
+
## Metrics
|
|
301
|
+
|
|
302
|
+
The state file tracks operational metrics:
|
|
303
|
+
|
|
304
|
+
- **totalFallbacks** — How many times the circuit opened
|
|
305
|
+
- **totalRecoveries** — How many times it recovered to preferred model
|
|
306
|
+
- **lastFallbackAt** — ISO timestamp of last rate limit event
|
|
307
|
+
- **lastRecoveryAt** — ISO timestamp of last successful recovery
|
|
308
|
+
|
|
309
|
+
Query metrics with:
|
|
310
|
+
```powershell
|
|
311
|
+
$cb = Get-Content .squad/ralph-circuit-breaker.json | ConvertFrom-Json
|
|
312
|
+
Write-Host "Fallbacks: $($cb.metrics.totalFallbacks) | Recoveries: $($cb.metrics.totalRecoveries)"
|
|
313
|
+
```
|
|
@@ -1,37 +1,37 @@
|
|
|
1
|
-
# Raw Agent Output — Appendix Format
|
|
2
|
-
|
|
3
|
-
> This template defines the format for the `## APPENDIX: RAW AGENT OUTPUTS` section
|
|
4
|
-
> in any multi-agent artifact.
|
|
5
|
-
|
|
6
|
-
## Rules
|
|
7
|
-
|
|
8
|
-
1. **Verbatim only.** Paste the agent's response exactly as returned. No edits.
|
|
9
|
-
2. **No summarizing.** Do not condense, paraphrase, or rephrase any part of the output.
|
|
10
|
-
3. **No rewriting.** Do not fix typos, grammar, formatting, or style.
|
|
11
|
-
4. **No code fences around the entire output.** The raw output is pasted as-is, not wrapped in ``` blocks.
|
|
12
|
-
5. **One section per agent.** Each agent that contributed gets its own heading.
|
|
13
|
-
6. **Order matches work order.** List agents in the order they were spawned.
|
|
14
|
-
7. **Include all outputs.** Even if an agent's work was rejected, include their output for diagnostic traceability.
|
|
15
|
-
|
|
16
|
-
## Format
|
|
17
|
-
|
|
18
|
-
```markdown
|
|
19
|
-
## APPENDIX: RAW AGENT OUTPUTS
|
|
20
|
-
|
|
21
|
-
### {Name} ({Role}) — Raw Output
|
|
22
|
-
|
|
23
|
-
{Paste agent's verbatim response here, unedited}
|
|
24
|
-
|
|
25
|
-
### {Name} ({Role}) — Raw Output
|
|
26
|
-
|
|
27
|
-
{Paste agent's verbatim response here, unedited}
|
|
28
|
-
```
|
|
29
|
-
|
|
30
|
-
## Why This Exists
|
|
31
|
-
|
|
32
|
-
The appendix provides diagnostic integrity. It lets anyone verify:
|
|
33
|
-
- What each agent actually said (vs. what the Coordinator assembled)
|
|
34
|
-
- Whether the Coordinator faithfully represented agent work
|
|
35
|
-
- What was lost or changed in synthesis
|
|
36
|
-
|
|
37
|
-
Without raw outputs, multi-agent collaboration is unauditable.
|
|
1
|
+
# Raw Agent Output — Appendix Format
|
|
2
|
+
|
|
3
|
+
> This template defines the format for the `## APPENDIX: RAW AGENT OUTPUTS` section
|
|
4
|
+
> in any multi-agent artifact.
|
|
5
|
+
|
|
6
|
+
## Rules
|
|
7
|
+
|
|
8
|
+
1. **Verbatim only.** Paste the agent's response exactly as returned. No edits.
|
|
9
|
+
2. **No summarizing.** Do not condense, paraphrase, or rephrase any part of the output.
|
|
10
|
+
3. **No rewriting.** Do not fix typos, grammar, formatting, or style.
|
|
11
|
+
4. **No code fences around the entire output.** The raw output is pasted as-is, not wrapped in ``` blocks.
|
|
12
|
+
5. **One section per agent.** Each agent that contributed gets its own heading.
|
|
13
|
+
6. **Order matches work order.** List agents in the order they were spawned.
|
|
14
|
+
7. **Include all outputs.** Even if an agent's work was rejected, include their output for diagnostic traceability.
|
|
15
|
+
|
|
16
|
+
## Format
|
|
17
|
+
|
|
18
|
+
```markdown
|
|
19
|
+
## APPENDIX: RAW AGENT OUTPUTS
|
|
20
|
+
|
|
21
|
+
### {Name} ({Role}) — Raw Output
|
|
22
|
+
|
|
23
|
+
{Paste agent's verbatim response here, unedited}
|
|
24
|
+
|
|
25
|
+
### {Name} ({Role}) — Raw Output
|
|
26
|
+
|
|
27
|
+
{Paste agent's verbatim response here, unedited}
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
## Why This Exists
|
|
31
|
+
|
|
32
|
+
The appendix provides diagnostic integrity. It lets anyone verify:
|
|
33
|
+
- What each agent actually said (vs. what the Coordinator assembled)
|
|
34
|
+
- Whether the Coordinator faithfully represented agent work
|
|
35
|
+
- What was lost or changed in synthesis
|
|
36
|
+
|
|
37
|
+
Without raw outputs, multi-agent collaboration is unauditable.
|
package/templates/roster.md
CHANGED
|
@@ -1,60 +1,60 @@
|
|
|
1
|
-
# Team Roster
|
|
2
|
-
|
|
3
|
-
> {One-line project description}
|
|
4
|
-
|
|
5
|
-
## Coordinator
|
|
6
|
-
|
|
7
|
-
| Name | Role | Notes |
|
|
8
|
-
|------|------|-------|
|
|
9
|
-
| Squad | Coordinator | Routes work, enforces handoffs and reviewer gates. Does not generate domain artifacts. |
|
|
10
|
-
|
|
11
|
-
## Members
|
|
12
|
-
|
|
13
|
-
| Name | Role | Charter | Status |
|
|
14
|
-
|------|------|---------|--------|
|
|
15
|
-
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
16
|
-
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
17
|
-
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
18
|
-
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
19
|
-
| Scribe | Session Logger | `.squad/agents/scribe/charter.md` | 📋 Silent |
|
|
20
|
-
| Ralph | Work Monitor | — | 🔄 Monitor |
|
|
21
|
-
|
|
22
|
-
## Coding Agent
|
|
23
|
-
|
|
24
|
-
<!-- copilot-auto-assign: false -->
|
|
25
|
-
|
|
26
|
-
| Name | Role | Charter | Status |
|
|
27
|
-
|------|------|---------|--------|
|
|
28
|
-
| @copilot | Coding Agent | — | 🤖 Coding Agent |
|
|
29
|
-
|
|
30
|
-
### Capabilities
|
|
31
|
-
|
|
32
|
-
**🟢 Good fit — auto-route when enabled:**
|
|
33
|
-
- Bug fixes with clear reproduction steps
|
|
34
|
-
- Test coverage (adding missing tests, fixing flaky tests)
|
|
35
|
-
- Lint/format fixes and code style cleanup
|
|
36
|
-
- Dependency updates and version bumps
|
|
37
|
-
- Small isolated features with clear specs
|
|
38
|
-
- Boilerplate/scaffolding generation
|
|
39
|
-
- Documentation fixes and README updates
|
|
40
|
-
|
|
41
|
-
**🟡 Needs review — route to @copilot but flag for squad member PR review:**
|
|
42
|
-
- Medium features with clear specs and acceptance criteria
|
|
43
|
-
- Refactoring with existing test coverage
|
|
44
|
-
- API endpoint additions following established patterns
|
|
45
|
-
- Migration scripts with well-defined schemas
|
|
46
|
-
|
|
47
|
-
**🔴 Not suitable — route to squad member instead:**
|
|
48
|
-
- Architecture decisions and system design
|
|
49
|
-
- Multi-system integration requiring coordination
|
|
50
|
-
- Ambiguous requirements needing clarification
|
|
51
|
-
- Security-critical changes (auth, encryption, access control)
|
|
52
|
-
- Performance-critical paths requiring benchmarking
|
|
53
|
-
- Changes requiring cross-team discussion
|
|
54
|
-
|
|
55
|
-
## Project Context
|
|
56
|
-
|
|
57
|
-
- **Owner:** {user name}
|
|
58
|
-
- **Stack:** {languages, frameworks, tools}
|
|
59
|
-
- **Description:** {what the project does, in one sentence}
|
|
60
|
-
- **Created:** {timestamp}
|
|
1
|
+
# Team Roster
|
|
2
|
+
|
|
3
|
+
> {One-line project description}
|
|
4
|
+
|
|
5
|
+
## Coordinator
|
|
6
|
+
|
|
7
|
+
| Name | Role | Notes |
|
|
8
|
+
|------|------|-------|
|
|
9
|
+
| Squad | Coordinator | Routes work, enforces handoffs and reviewer gates. Does not generate domain artifacts. |
|
|
10
|
+
|
|
11
|
+
## Members
|
|
12
|
+
|
|
13
|
+
| Name | Role | Charter | Status |
|
|
14
|
+
|------|------|---------|--------|
|
|
15
|
+
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
16
|
+
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
17
|
+
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
18
|
+
| {Name} | {Role} | `.squad/agents/{name}/charter.md` | ✅ Active |
|
|
19
|
+
| Scribe | Session Logger | `.squad/agents/scribe/charter.md` | 📋 Silent |
|
|
20
|
+
| Ralph | Work Monitor | — | 🔄 Monitor |
|
|
21
|
+
|
|
22
|
+
## Coding Agent
|
|
23
|
+
|
|
24
|
+
<!-- copilot-auto-assign: false -->
|
|
25
|
+
|
|
26
|
+
| Name | Role | Charter | Status |
|
|
27
|
+
|------|------|---------|--------|
|
|
28
|
+
| @copilot | Coding Agent | — | 🤖 Coding Agent |
|
|
29
|
+
|
|
30
|
+
### Capabilities
|
|
31
|
+
|
|
32
|
+
**🟢 Good fit — auto-route when enabled:**
|
|
33
|
+
- Bug fixes with clear reproduction steps
|
|
34
|
+
- Test coverage (adding missing tests, fixing flaky tests)
|
|
35
|
+
- Lint/format fixes and code style cleanup
|
|
36
|
+
- Dependency updates and version bumps
|
|
37
|
+
- Small isolated features with clear specs
|
|
38
|
+
- Boilerplate/scaffolding generation
|
|
39
|
+
- Documentation fixes and README updates
|
|
40
|
+
|
|
41
|
+
**🟡 Needs review — route to @copilot but flag for squad member PR review:**
|
|
42
|
+
- Medium features with clear specs and acceptance criteria
|
|
43
|
+
- Refactoring with existing test coverage
|
|
44
|
+
- API endpoint additions following established patterns
|
|
45
|
+
- Migration scripts with well-defined schemas
|
|
46
|
+
|
|
47
|
+
**🔴 Not suitable — route to squad member instead:**
|
|
48
|
+
- Architecture decisions and system design
|
|
49
|
+
- Multi-system integration requiring coordination
|
|
50
|
+
- Ambiguous requirements needing clarification
|
|
51
|
+
- Security-critical changes (auth, encryption, access control)
|
|
52
|
+
- Performance-critical paths requiring benchmarking
|
|
53
|
+
- Changes requiring cross-team discussion
|
|
54
|
+
|
|
55
|
+
## Project Context
|
|
56
|
+
|
|
57
|
+
- **Owner:** {user name}
|
|
58
|
+
- **Stack:** {languages, frameworks, tools}
|
|
59
|
+
- **Description:** {what the project does, in one sentence}
|
|
60
|
+
- **Created:** {timestamp}
|
package/templates/routing.md
CHANGED
|
@@ -1,54 +1,39 @@
|
|
|
1
|
-
# Work Routing
|
|
2
|
-
|
|
3
|
-
How to decide who handles what.
|
|
4
|
-
|
|
5
|
-
## Routing Table
|
|
6
|
-
|
|
7
|
-
| Work Type | Route To | Examples |
|
|
8
|
-
|-----------|----------|----------|
|
|
9
|
-
| {domain 1} | {Name} | {example tasks} |
|
|
10
|
-
| {domain 2} | {Name} | {example tasks} |
|
|
11
|
-
| {domain 3} | {Name} | {example tasks} |
|
|
12
|
-
| Code review | {Name} | Review PRs, check quality, suggest improvements |
|
|
13
|
-
| Testing | {Name} | Write tests, find edge cases, verify fixes |
|
|
14
|
-
| Scope & priorities | {Name} | What to build next, trade-offs, decisions |
|
|
15
|
-
|
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
| `squad` |
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
2. **Does it follow existing patterns?** Adding a test, fixing a known bug, updating a dependency → likely 🟢
|
|
41
|
-
3. **Does it need design judgment?** Architecture, API design, UX decisions → likely 🔴
|
|
42
|
-
4. **Is it security-sensitive?** Auth, encryption, access control → always 🔴
|
|
43
|
-
5. **Is it medium complexity with specs?** Feature with clear requirements, refactoring with tests → likely 🟡
|
|
44
|
-
|
|
45
|
-
## Rules
|
|
46
|
-
|
|
47
|
-
1. **Eager by default** — spawn all agents who could usefully start work, including anticipatory downstream work.
|
|
48
|
-
2. **Scribe always runs** after substantial work, always as `mode: "background"`. Never blocks.
|
|
49
|
-
3. **Quick facts → coordinator answers directly.** Don't spawn an agent for "what port does the server run on?"
|
|
50
|
-
4. **When two agents could handle it**, pick the one whose domain is the primary concern.
|
|
51
|
-
5. **"Team, ..." → fan-out.** Spawn all relevant agents in parallel as `mode: "background"`.
|
|
52
|
-
6. **Anticipate downstream work.** If a feature is being built, spawn the tester to write test cases from requirements simultaneously.
|
|
53
|
-
7. **Issue-labeled work** — when a `squad:{member}` label is applied to an issue, route to that member. The Lead handles all `squad` (base label) triage.
|
|
54
|
-
8. **@copilot routing** — when evaluating issues, check @copilot's capability profile in `team.md`. Route 🟢 good-fit tasks to `squad:copilot`. Flag 🟡 needs-review tasks for PR review. Keep 🔴 not-suitable tasks with squad members.
|
|
1
|
+
# Work Routing
|
|
2
|
+
|
|
3
|
+
How to decide who handles what.
|
|
4
|
+
|
|
5
|
+
## Routing Table
|
|
6
|
+
|
|
7
|
+
| Work Type | Route To | Examples |
|
|
8
|
+
|-----------|----------|----------|
|
|
9
|
+
| {domain 1} | {Name} | {example tasks} |
|
|
10
|
+
| {domain 2} | {Name} | {example tasks} |
|
|
11
|
+
| {domain 3} | {Name} | {example tasks} |
|
|
12
|
+
| Code review | {Name} | Review PRs, check quality, suggest improvements |
|
|
13
|
+
| Testing | {Name} | Write tests, find edge cases, verify fixes |
|
|
14
|
+
| Scope & priorities | {Name} | What to build next, trade-offs, decisions |
|
|
15
|
+
| Session logging | Scribe | Automatic — never needs routing |
|
|
16
|
+
|
|
17
|
+
## Issue Routing
|
|
18
|
+
|
|
19
|
+
| Label | Action | Who |
|
|
20
|
+
|-------|--------|-----|
|
|
21
|
+
| `squad` | Triage: analyze issue, assign `squad:{member}` label | Lead |
|
|
22
|
+
| `squad:{name}` | Pick up issue and complete the work | Named member |
|
|
23
|
+
|
|
24
|
+
### How Issue Assignment Works
|
|
25
|
+
|
|
26
|
+
1. When a GitHub issue gets the `squad` label, the **Lead** triages it — analyzing content, assigning the right `squad:{member}` label, and commenting with triage notes.
|
|
27
|
+
2. When a `squad:{member}` label is applied, that member picks up the issue in their next session.
|
|
28
|
+
3. Members can reassign by removing their label and adding another member's label.
|
|
29
|
+
4. The `squad` label is the "inbox" — untriaged issues waiting for Lead review.
|
|
30
|
+
|
|
31
|
+
## Rules
|
|
32
|
+
|
|
33
|
+
1. **Eager by default** — spawn all agents who could usefully start work, including anticipatory downstream work.
|
|
34
|
+
2. **Scribe always runs** after substantial work, always as `mode: "background"`. Never blocks.
|
|
35
|
+
3. **Quick facts → coordinator answers directly.** Don't spawn an agent for "what port does the server run on?"
|
|
36
|
+
4. **When two agents could handle it**, pick the one whose domain is the primary concern.
|
|
37
|
+
5. **"Team, ..." → fan-out.** Spawn all relevant agents in parallel as `mode: "background"`.
|
|
38
|
+
6. **Anticipate downstream work.** If a feature is being built, spawn the tester to write test cases from requirements simultaneously.
|
|
39
|
+
7. **Issue-labeled work** — when a `squad:{member}` label is applied to an issue, route to that member. The Lead handles all `squad` (base label) triage.
|