@mmerterden/multi-agent-pipeline 13.5.0 → 14.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (119) hide show
  1. package/CHANGELOG.md +243 -0
  2. package/README.md +3 -3
  3. package/docs/features.md +1 -1
  4. package/install/_common.mjs +73 -0
  5. package/install/_mcp-register.mjs +70 -31
  6. package/install/_plugin-skills.mjs +73 -14
  7. package/install/claude.mjs +28 -4
  8. package/install/codex.mjs +33 -2
  9. package/install/copilot.mjs +145 -9
  10. package/install/index.mjs +10 -6
  11. package/install/templates/copilot-instructions.md +1 -1
  12. package/package.json +1 -1
  13. package/pipeline/agents/code-reviewer.md +58 -1
  14. package/pipeline/commands/multi-agent/SKILL.md +7 -5
  15. package/pipeline/commands/multi-agent/analysis/SKILL.md +7 -7
  16. package/pipeline/commands/multi-agent/analysis-resolve/SKILL.md +1 -1
  17. package/pipeline/commands/multi-agent/build-optimize/SKILL.md +7 -7
  18. package/pipeline/commands/multi-agent/channels/SKILL.md +5 -5
  19. package/pipeline/commands/multi-agent/dev/SKILL.md +23 -18
  20. package/pipeline/commands/multi-agent/dev-autopilot/SKILL.md +19 -13
  21. package/pipeline/commands/multi-agent/dev-local/SKILL.md +14 -12
  22. package/pipeline/commands/multi-agent/dev-local-autopilot/SKILL.md +17 -12
  23. package/pipeline/commands/multi-agent/garbage-collect/SKILL.md +1 -1
  24. package/pipeline/commands/multi-agent/help/SKILL.md +4 -4
  25. package/pipeline/commands/multi-agent/ios-coding-standard/SKILL.md +2 -2
  26. package/pipeline/commands/multi-agent/local-autopilot/SKILL.md +4 -4
  27. package/pipeline/commands/multi-agent/resume/SKILL.md +1 -1
  28. package/pipeline/commands/multi-agent/review/SKILL.md +5 -5
  29. package/pipeline/commands/multi-agent/scan/SKILL.md +1 -1
  30. package/pipeline/commands/multi-agent/search/SKILL.md +1 -1
  31. package/pipeline/commands/multi-agent/setup/SKILL.md +6 -6
  32. package/pipeline/commands/multi-agent/{finish → ship}/SKILL.md +12 -12
  33. package/pipeline/commands/multi-agent/testflight-validation/SKILL.md +1 -1
  34. package/pipeline/commands/multi-agent/update/SKILL.md +5 -2
  35. package/pipeline/commands/sim-test.md +2 -2
  36. package/pipeline/lib/credential-store-resolver.sh +16 -0
  37. package/pipeline/lib/credential-store.sh +47 -4
  38. package/pipeline/lib/fetch-figma-annotations.sh +26 -28
  39. package/pipeline/lib/figma-screenshot.sh +28 -39
  40. package/pipeline/lib/figma-token.sh +63 -0
  41. package/pipeline/multi-agent-refs/analysis-template.md +1 -1
  42. package/pipeline/multi-agent-refs/android-guide.md +1 -1
  43. package/pipeline/multi-agent-refs/channels/issue-comment.md +1 -1
  44. package/pipeline/multi-agent-refs/component-dispatch.md +2 -2
  45. package/pipeline/multi-agent-refs/cross-cli-contract.md +4 -4
  46. package/pipeline/multi-agent-refs/features/dev-critic.md +2 -2
  47. package/pipeline/multi-agent-refs/features/model-fallback.md +35 -2
  48. package/pipeline/multi-agent-refs/features/plan-todos.md +1 -1
  49. package/pipeline/multi-agent-refs/features/repo-map.md +1 -1
  50. package/pipeline/multi-agent-refs/features/review-multi-repo.md +3 -3
  51. package/pipeline/multi-agent-refs/features/shadow-git.md +1 -1
  52. package/pipeline/multi-agent-refs/features/skill-conformance.md +116 -0
  53. package/pipeline/multi-agent-refs/features/verify-by-test.md +1 -1
  54. package/pipeline/multi-agent-refs/generate-issue.md +1 -1
  55. package/pipeline/multi-agent-refs/multi-repo-integration-build.md +1 -1
  56. package/pipeline/multi-agent-refs/phases/log-format.md +4 -4
  57. package/pipeline/multi-agent-refs/phases/modes.md +7 -7
  58. package/pipeline/multi-agent-refs/phases/phase-0-init.md +13 -11
  59. package/pipeline/multi-agent-refs/phases/phase-1-analysis.md +17 -15
  60. package/pipeline/multi-agent-refs/phases/phase-2-planning.md +7 -7
  61. package/pipeline/multi-agent-refs/phases/phase-3-dev.md +28 -13
  62. package/pipeline/multi-agent-refs/phases/phase-4-review.md +90 -58
  63. package/pipeline/multi-agent-refs/phases/phase-5-test.md +7 -7
  64. package/pipeline/multi-agent-refs/phases/phase-6-commit.md +8 -8
  65. package/pipeline/multi-agent-refs/phases/phase-7-report.md +8 -8
  66. package/pipeline/multi-agent-refs/phases.md +13 -13
  67. package/pipeline/multi-agent-refs/progress-contract.md +2 -2
  68. package/pipeline/multi-agent-refs/rules.md +7 -5
  69. package/pipeline/multi-agent-refs/swiftui-guide.md +1 -1
  70. package/pipeline/multi-agent-refs/tracker-contract.md +16 -15
  71. package/pipeline/preferences-template.json +7 -1
  72. package/pipeline/rules/figma-pipeline.md +2 -2
  73. package/pipeline/schemas/agent-state.schema.json +333 -79
  74. package/pipeline/schemas/criteria-manifest.schema.json +228 -0
  75. package/pipeline/schemas/migrations/prefs-2.4.0-to-2.5.0.mjs +64 -0
  76. package/pipeline/schemas/prefs.schema.json +118 -262
  77. package/pipeline/schemas/reviewer-output.schema.json +48 -3
  78. package/pipeline/schemas/token-budget.json +34 -10
  79. package/pipeline/schemas/triage-output.schema.json +112 -27
  80. package/pipeline/scripts/cost-table.json +7 -4
  81. package/pipeline/scripts/gc-worktrees.sh +1 -1
  82. package/pipeline/scripts/gen-mode-dispatch.mjs +6 -6
  83. package/pipeline/scripts/match-skills.mjs +37 -4
  84. package/pipeline/scripts/migrate-prefs.mjs +88 -17
  85. package/pipeline/scripts/phase-tracker.sh +14 -3
  86. package/pipeline/scripts/pre-commit-check.sh +49 -2
  87. package/pipeline/scripts/skill-conformance.mjs +960 -0
  88. package/pipeline/scripts/smoke-schema-validation.sh +17 -4
  89. package/pipeline/scripts/uninstall.mjs +35 -9
  90. package/pipeline/scripts/validate-reviewer.mjs +108 -1
  91. package/pipeline/skills/.skill-manifest.json +1 -1
  92. package/pipeline/skills/.skills-index.json +36 -9
  93. package/pipeline/skills/shared/README.md +15 -12
  94. package/pipeline/skills/shared/core/apple-archive-compliance/SKILL.md +1 -0
  95. package/pipeline/skills/shared/core/apple-archive-compliance/references/rules.yml +167 -0
  96. package/pipeline/skills/shared/core/google-play-compliance/SKILL.md +1 -0
  97. package/pipeline/skills/shared/core/google-play-compliance/references/rules.yml +184 -0
  98. package/pipeline/skills/shared/core/multi-agent/SKILL.md +10 -10
  99. package/pipeline/skills/shared/core/multi-agent-analysis/SKILL.md +4 -4
  100. package/pipeline/skills/shared/core/multi-agent-analysis-resolve/SKILL.md +3 -3
  101. package/pipeline/skills/shared/core/multi-agent-build-optimize/SKILL.md +2 -2
  102. package/pipeline/skills/shared/core/multi-agent-create-jira/SKILL.md +1 -1
  103. package/pipeline/skills/shared/core/multi-agent-dev/SKILL.md +6 -5
  104. package/pipeline/skills/shared/core/multi-agent-dev-autopilot/SKILL.md +7 -6
  105. package/pipeline/skills/shared/core/multi-agent-dev-local/SKILL.md +4 -3
  106. package/pipeline/skills/shared/core/multi-agent-dev-local-autopilot/SKILL.md +2 -1
  107. package/pipeline/skills/shared/core/multi-agent-help/SKILL.md +2 -2
  108. package/pipeline/skills/shared/core/multi-agent-ios-coding-standard/SKILL.md +1 -1
  109. package/pipeline/skills/shared/core/multi-agent-local-autopilot/SKILL.md +4 -4
  110. package/pipeline/skills/shared/core/multi-agent-review/SKILL.md +5 -5
  111. package/pipeline/skills/shared/core/multi-agent-scan/SKILL.md +1 -1
  112. package/pipeline/skills/shared/core/multi-agent-search/SKILL.md +1 -1
  113. package/pipeline/skills/shared/core/{multi-agent-finish → multi-agent-ship}/SKILL.md +8 -8
  114. package/pipeline/skills/shared/external/ios-coding-standard/SKILL.md +44 -5
  115. package/pipeline/skills/shared/external/ios-coding-standard/modules/_TEMPLATE.yml +82 -0
  116. package/pipeline/skills/shared/external/ios-coding-standard/references/STANDARD.md +169 -10
  117. package/pipeline/skills/shared/external/ios-coding-standard/references/lint-local.sh +13 -1
  118. package/pipeline/skills/shared/external/ios-coding-standard/references/rules.yml +335 -16
  119. package/pipeline/skills/skills-index.md +11 -8
@@ -10,22 +10,12 @@
10
10
  "description": "Documentation-only blocks shipped in preferences-template.json (_figmaConfigTemplate, _derivedSkillSourcesTemplate, _devToolkitTemplate). Copy-paste examples, never read by the pipeline."
11
11
  }
12
12
  },
13
- "required": [
14
- "schemaVersion",
15
- "global",
16
- "projects"
17
- ],
13
+ "required": ["schemaVersion", "global", "projects"],
18
14
  "properties": {
19
15
  "schemaVersion": {
20
16
  "type": "string",
21
- "enum": [
22
- "2.0.0",
23
- "2.1.0",
24
- "2.2.0",
25
- "2.3.0",
26
- "2.4.0"
27
- ],
28
- "description": "v2.0.0: pre-v3.7. v2.1.0: v3.7+ adds identities[].servicePatMap, platformIdentityRouting, recentGroups, recentBranches, serviceStatus, settings, expanded keychainMapping. v2.2.0: v6.0.0 formalizes v5.7 / v5.8 additions (reportChannels, reportContent with technicalAnalysis, wikiScope, autopilotReportTimeoutSeconds) that had been running as 2.1.0 sub-migrations without a proper version bump."
17
+ "enum": ["2.0.0", "2.1.0", "2.2.0", "2.3.0", "2.4.0", "2.5.0"],
18
+ "description": "v2.0.0: pre-v3.7. v2.1.0: v3.7+ adds identities[].servicePatMap, platformIdentityRouting, recentGroups, recentBranches, serviceStatus, settings, expanded keychainMapping. v2.2.0: v6.0.0 formalizes v5.7 / v5.8 additions (reportChannels, reportContent with technicalAnalysis, wikiScope, autopilotReportTimeoutSeconds) that had been running as 2.1.0 sub-migrations without a proper version bump. v2.5.0: v14.0.0 adds global.skillConformance (Phase 4 criteria resolution) and declares global.ship.autoFix, which the tail command's spec had referenced as global.finish.autoFix without ever declaring it."
29
19
  },
30
20
  "global": {
31
21
  "type": "object",
@@ -37,10 +27,7 @@
37
27
  "items": {
38
28
  "type": "object",
39
29
  "additionalProperties": false,
40
- "required": [
41
- "name",
42
- "email"
43
- ],
30
+ "required": ["name", "email"],
44
31
  "properties": {
45
32
  "name": {
46
33
  "type": "string"
@@ -88,6 +75,21 @@
88
75
  },
89
76
  "jenkins": {
90
77
  "type": "string"
78
+ },
79
+ "figma_pat": {
80
+ "type": "string",
81
+ "deprecated": true,
82
+ "description": "DEPRECATED, pre-v13.6 name for `figma`. Declared only so a pre-migration identity still validates; `migrate-prefs.mjs` copies the value into `figma` and deletes this key."
83
+ },
84
+ "firebase_sa": {
85
+ "type": "string",
86
+ "deprecated": true,
87
+ "description": "DEPRECATED, early-v2.1.0 name for `firebase`. Declared only so a pre-consolidation identity still validates; `migrate-prefs.mjs` copies the value into `firebase` and deletes this key."
88
+ },
89
+ "firebase_project": {
90
+ "type": "string",
91
+ "deprecated": true,
92
+ "description": "DEPRECATED and unused. Declared only so a pre-consolidation identity still validates; `migrate-prefs.mjs` removes it."
91
93
  }
92
94
  }
93
95
  }
@@ -106,143 +108,94 @@
106
108
  "keychainMapping": {
107
109
  "type": "object",
108
110
  "additionalProperties": false,
109
- "description": "Maps logical token names to actual Keychain item names. Pipeline looks up tokens via `security find-generic-password -s <mapped-name>` (or `pipeline/lib/credential-store.sh get` cross-platform). Covered keys: jira, bitbucket, bitbucket_token, bitbucket_user, github, confluence, figma, figma_pat, figma_user, figma_mcp, fortify, graylog, firebase, jenkins, npm, claude_oauth_token, claude_oauth_token_fallback.",
111
+ "description": "Maps logical token names to actual Keychain item names. Pipeline looks up tokens via `security find-generic-password -s <mapped-name>` (or `pipeline/lib/credential-store.sh get` cross-platform). Covered keys: jira, bitbucket, bitbucket_token, bitbucket_user, github, confluence, figma, figma_mcp, fortify, graylog, firebase, jenkins, npm, claude_oauth_token, claude_oauth_token_fallback. Deprecated and accepted only for backward compatibility: figma_pat (superseded by figma), figma_user (unused).",
110
112
  "properties": {
111
113
  "jira": {
112
- "type": [
113
- "string",
114
- "null"
115
- ]
114
+ "type": ["string", "null"]
116
115
  },
117
116
  "bitbucket": {
118
- "type": [
119
- "string",
120
- "null"
121
- ],
117
+ "type": ["string", "null"],
122
118
  "description": "Legacy alias for bitbucket_token."
123
119
  },
124
120
  "bitbucket_token": {
125
- "type": [
126
- "string",
127
- "null"
128
- ]
121
+ "type": ["string", "null"]
129
122
  },
130
123
  "bitbucket_user": {
131
- "type": [
132
- "string",
133
- "null"
134
- ]
124
+ "type": ["string", "null"]
135
125
  },
136
126
  "github": {
137
- "type": [
138
- "string",
139
- "null"
140
- ]
127
+ "type": ["string", "null"]
141
128
  },
142
129
  "confluence": {
143
- "type": [
144
- "string",
145
- "null"
146
- ]
130
+ "type": ["string", "null"]
147
131
  },
148
132
  "figma": {
149
- "type": [
150
- "string",
151
- "null"
152
- ]
133
+ "type": ["string", "null"],
134
+ "description": "Figma Personal Access Token. The canonical Tier 2 (REST API) key of the Figma access chain - this is the key `figma-token.sh` resolves. Supersedes `figma_pat`."
153
135
  },
154
136
  "figma_mcp": {
155
- "type": [
156
- "string",
157
- "null"
158
- ]
137
+ "type": ["string", "null"],
138
+ "description": "Figma MCP token. Tier 1 of the Figma access chain. The `mcp__claude_ai_Figma__*` calls themselves authenticate through Anthropic-managed MCP auth, but the token must be onboarded so that flow has something to bind to, and so `lib/figma-mcp-refresh.sh` can renew it."
159
139
  },
160
140
  "fortify": {
161
- "type": [
162
- "string",
163
- "null"
164
- ]
141
+ "type": ["string", "null"]
165
142
  },
166
143
  "graylog": {
167
- "type": [
168
- "string",
169
- "null"
170
- ]
144
+ "type": ["string", "null"]
171
145
  },
172
146
  "figma_pat": {
173
- "type": [
174
- "string",
175
- "null"
176
- ],
177
- "description": "Figma Personal Access Token. Tier 2 of the Figma access chain (REST API) resolves this key."
147
+ "type": ["string", "null"],
148
+ "deprecated": true,
149
+ "description": "DEPRECATED, pre-v13.6 name for `figma`. Kept so an un-migrated preferences file still validates; `migrate-prefs.mjs` copies the value into `figma` and deletes this key. Never write a new mapping here - the next migration removes it. Runtime lookups read `figma` first and fall back to this key only for installs that have not migrated yet."
178
150
  },
179
151
  "figma_user": {
180
- "type": [
181
- "string",
182
- "null"
183
- ],
184
- "description": "Figma account identifier, when the REST flow needs it alongside figma_pat."
152
+ "type": ["string", "null"],
153
+ "deprecated": true,
154
+ "description": "DEPRECATED and unused. `migrate-prefs.mjs` removes this key; the REST flow authenticates with the PAT alone."
185
155
  },
186
156
  "claude_oauth_token": {
187
- "type": [
188
- "string",
189
- "null"
190
- ],
157
+ "type": ["string", "null"],
191
158
  "description": "Claude Code OAuth token used by headless / scheduled runs."
192
159
  },
193
160
  "claude_oauth_token_fallback": {
194
- "type": [
195
- "string",
196
- "null"
197
- ],
161
+ "type": ["string", "null"],
198
162
  "description": "Secondary OAuth token used when the primary is rate-limited or expired."
199
163
  },
200
164
  "firebase": {
201
- "type": [
202
- "string",
203
- "null"
204
- ],
165
+ "type": ["string", "null"],
205
166
  "description": "Firebase JSON (base64-encoded). project_id is parsed from the decoded JSON."
206
167
  },
168
+ "firebase_sa": {
169
+ "type": ["string", "null"],
170
+ "deprecated": true,
171
+ "description": "DEPRECATED, early-v2.1.0 name for `firebase`. Declared only so a pre-consolidation preferences file still validates long enough for `migrate-prefs.mjs` to copy the value into `firebase` and delete this key. Never write a new mapping here."
172
+ },
173
+ "firebase_project": {
174
+ "type": ["string", "null"],
175
+ "deprecated": true,
176
+ "description": "DEPRECATED and unused. Declared only so a pre-consolidation preferences file still validates; `migrate-prefs.mjs` removes it, because project_id is parsed from the decoded service-account JSON and needs no separate entry."
177
+ },
207
178
  "jenkins": {
208
- "type": [
209
- "string",
210
- "null"
211
- ]
179
+ "type": ["string", "null"]
212
180
  },
213
181
  "npm": {
214
- "type": [
215
- "string",
216
- "null"
217
- ],
182
+ "type": ["string", "null"],
218
183
  "description": "NPM registry token (npm.pkg.github.com or npmjs.com). Used by package publish flow."
219
184
  },
220
185
  "appstore_connect_key_id": {
221
- "type": [
222
- "string",
223
- "null"
224
- ],
186
+ "type": ["string", "null"],
225
187
  "description": "App Store Connect API key ID. Tier 1 of the App Store Connect access chain, used by /multi-agent:testflight-validation Gate 2. An identifier rather than a secret; mapped anyway so every credential is read through the same layer. Creating an API key needs an Admin or App Manager role, which is why Tier 2 exists."
226
188
  },
227
189
  "appstore_connect_issuer_id": {
228
- "type": [
229
- "string",
230
- "null"
231
- ],
190
+ "type": ["string", "null"],
232
191
  "description": "App Store Connect API issuer ID. Required alongside appstore_connect_key_id; either alone leaves Tier 1 unusable and the resolver says so instead of silently dropping to Tier 2. The .p8 private key is a FILE and is never stored here - it belongs at ~/.appstoreconnect/private_keys/AuthKey_<keyId>.p8, one of the directories altool searches."
233
192
  },
234
193
  "appstore_connect_apple_id": {
235
- "type": [
236
- "string",
237
- "null"
238
- ],
194
+ "type": ["string", "null"],
239
195
  "description": "Apple ID for Tier 2 of the App Store Connect access chain. Usable by any Apple ID holder with no elevated role, which is the realistic path when API-key creation is not permitted on the account."
240
196
  },
241
197
  "appstore_connect_password_item": {
242
- "type": [
243
- "string",
244
- "null"
245
- ],
198
+ "type": ["string", "null"],
246
199
  "description": "Name of the keychain item holding the app-specific password, created by `altool --store-password-in-keychain-item`. Holds an ITEM NAME, not a password: altool reads the secret itself via `-p @keychain:<item>`, so the value never reaches an argument list or the pipeline."
247
200
  }
248
201
  }
@@ -250,10 +203,7 @@
250
203
  "tokenScripts": {
251
204
  "type": "object",
252
205
  "additionalProperties": {
253
- "type": [
254
- "string",
255
- "null"
256
- ]
206
+ "type": ["string", "null"]
257
207
  },
258
208
  "default": {},
259
209
  "description": "Maps service ids to user-owned token generation scripts (absolute paths, personal - never synced). Used by the Phase 0 token pre-flight: figma_mcp silent renewal reads the .figma-oauth.json next to tokenScripts.figma_mcp; the 'Regenerate now (script)' option runs the script itself."
@@ -283,9 +233,7 @@
283
233
  {
284
234
  "type": "object",
285
235
  "additionalProperties": false,
286
- "required": [
287
- "path"
288
- ],
236
+ "required": ["path"],
289
237
  "properties": {
290
238
  "path": {
291
239
  "type": "string"
@@ -315,9 +263,7 @@
315
263
  "items": {
316
264
  "type": "object",
317
265
  "additionalProperties": false,
318
- "required": [
319
- "branch"
320
- ],
266
+ "required": ["branch"],
321
267
  "properties": {
322
268
  "branch": {
323
269
  "type": "string"
@@ -342,10 +288,7 @@
342
288
  "items": {
343
289
  "type": "object",
344
290
  "additionalProperties": false,
345
- "required": [
346
- "name",
347
- "description"
348
- ],
291
+ "required": ["name", "description"],
349
292
  "properties": {
350
293
  "name": {
351
294
  "type": "string",
@@ -366,10 +309,7 @@
366
309
  "description": "Where the routine came from, e.g. a CLAUDE.md section name or 'user'."
367
310
  },
368
311
  "trigger": {
369
- "type": [
370
- "string",
371
- "null"
372
- ],
312
+ "type": ["string", "null"],
373
313
  "description": "Optional natural-language trigger phrase the routine captures."
374
314
  }
375
315
  }
@@ -381,9 +321,7 @@
381
321
  "items": {
382
322
  "type": "object",
383
323
  "additionalProperties": false,
384
- "required": [
385
- "repos"
386
- ],
324
+ "required": ["repos"],
387
325
  "properties": {
388
326
  "label": {
389
327
  "type": "string",
@@ -415,9 +353,7 @@
415
353
  "items": {
416
354
  "type": "object",
417
355
  "additionalProperties": false,
418
- "required": [
419
- "repoSet"
420
- ],
356
+ "required": ["repoSet"],
421
357
  "properties": {
422
358
  "repoSet": {
423
359
  "type": "array",
@@ -437,11 +373,7 @@
437
373
  },
438
374
  "platform": {
439
375
  "type": "string",
440
- "enum": [
441
- "ios",
442
- "android",
443
- "mixed"
444
- ]
376
+ "enum": ["ios", "android", "mixed"]
445
377
  },
446
378
  "hostScheme": {
447
379
  "type": "string",
@@ -473,11 +405,7 @@
473
405
  },
474
406
  "lastResult": {
475
407
  "type": "string",
476
- "enum": [
477
- "success",
478
- "failed",
479
- "skipped"
480
- ]
408
+ "enum": ["success", "failed", "skipped"]
481
409
  }
482
410
  }
483
411
  },
@@ -489,10 +417,7 @@
489
417
  "additionalProperties": {
490
418
  "type": "object",
491
419
  "additionalProperties": false,
492
- "required": [
493
- "ok",
494
- "checkedAt"
495
- ],
420
+ "required": ["ok", "checkedAt"],
496
421
  "properties": {
497
422
  "ok": {
498
423
  "type": "boolean"
@@ -566,10 +491,7 @@
566
491
  }
567
492
  },
568
493
  "defaultJiraKey": {
569
- "type": [
570
- "string",
571
- "null"
572
- ],
494
+ "type": ["string", "null"],
573
495
  "description": "Default Jira project key used for placeholder replacement. null until /multi-agent:setup onboards a Jira project."
574
496
  },
575
497
  "modelFallback": {
@@ -583,10 +505,7 @@
583
505
  "description": "Master switch for tier fallback."
584
506
  },
585
507
  "premiumTierUntil": {
586
- "type": [
587
- "string",
588
- "null"
589
- ],
508
+ "type": ["string", "null"],
590
509
  "description": "ISO date after which the premium tier is assumed gone. null = no expiry known."
591
510
  },
592
511
  "fallbackModel": {
@@ -726,28 +645,14 @@
726
645
  "type": "array",
727
646
  "items": {
728
647
  "type": "string",
729
- "enum": [
730
- "main",
731
- "ios",
732
- "screenshots",
733
- "index"
734
- ]
648
+ "enum": ["main", "ios", "screenshots", "index"]
735
649
  },
736
- "default": [
737
- "main",
738
- "ios",
739
- "screenshots",
740
- "index"
741
- ],
650
+ "default": ["main", "ios", "screenshots", "index"],
742
651
  "description": "v5.7+ - Wiki Case A scope multi-select default'u. Component wiki dispatch'inde hangi artifact'lar yaz\u0131lacak: main (ana component sayfas\u0131), ios (iOS sub-page), screenshots (assets/ klas\u00f6r\u00fc), index (_Sidebar.md + ComponentImplementationStatus.md). Legacy wikiDefault=true \u2192 [main,ios,screenshots,index] migration; wikiDefault=false \u2192 [] (empty array = Wiki adapter Case B men\u00fcs\u00fcne d\u00fc\u015fer)."
743
652
  },
744
653
  "autoJiraFromGithubIssue": {
745
654
  "type": "string",
746
- "enum": [
747
- "ask",
748
- "always",
749
- "never"
750
- ],
655
+ "enum": ["ask", "always", "never"],
751
656
  "default": "ask",
752
657
  "description": "Policy for the GitHub-issue Jira auto-create (WS-6 triad, Phase 0 Step 1). `ask` prompts the user when a GitHub issue has no Jira ID. `always` auto-creates silently (and patches the GitHub issue body with the link). `never` skips and uses the `feature/GH{issueNo}-kebab` branch. Autopilot treats `ask` as `always` - there is no interactive fallback when running unattended."
753
658
  },
@@ -758,29 +663,19 @@
758
663
  },
759
664
  "promptLanguage": {
760
665
  "type": "string",
761
- "enum": [
762
- "en",
763
- "tr"
764
- ],
666
+ "enum": ["en", "tr"],
765
667
  "default": "en",
766
668
  "description": "Language used for user-facing INTERACTIVE pipeline copy: pickers (account, project, dev-context, base branch, branch name, maturity ack, channels), Phase 5 test prompt, Phase 6 local-checkout prompt, Phase 6 commit/PR confirmations, TaskCreate card subjects, and phase-banner.sh headers (`PHASE_LANG` resolves from this field via the `auto` sentinel). Canonical label table lives in `pipeline/skills/shared/multi-agent/SKILL.md`. External payloads stay English regardless of this setting: reviewer/triage system prompts, commit messages, PR titles/bodies, Jira comments, wiki content, agent-log.md payloads. Set via `/multi-agent:language prompt <en|tr>` or answered on first run by `/multi-agent:setup`."
767
669
  },
768
670
  "outputLanguage": {
769
671
  "type": "string",
770
- "enum": [
771
- "en",
772
- "tr"
773
- ],
672
+ "enum": ["en", "tr"],
774
673
  "default": "en",
775
674
  "description": "Language used for the assistant's NON-INTERACTIVE explanations, status updates, error messages, and pipeline-generated reports rendered to the user (e.g. `/multi-agent:help` body, `/multi-agent:status` table headers, summary blocks at the end of a run). Independent of `promptLanguage` so a user can have Turkish pickers but English summaries (or vice versa). External payloads (commits, PR/Jira/wiki) and skill-picker / confirmation / error UI exposed by the CLI host stay English regardless of this setting. Set via `/multi-agent:language output <en|tr>` or answered on first run by `/multi-agent:setup`."
776
675
  },
777
676
  "progressVerbosity": {
778
677
  "type": "string",
779
- "enum": [
780
- "quiet",
781
- "normal",
782
- "verbose"
783
- ],
678
+ "enum": ["quiet", "normal", "verbose"],
784
679
  "default": "normal",
785
680
  "description": "Verbosity of the live progress-line contract (`refs/progress-contract.md`). `quiet` shows only phase banners and user prompts (CI-friendly). `normal` shows banners + the canonical action set per phase - recommended for interactive use. `verbose` shows sub-agent internal actions, file-level reads, schema validations, retry internals - forced automatically when `mode: autopilot` is set in agent state so the run remains audit-grade when the user isn't watching live."
786
681
  },
@@ -803,9 +698,7 @@
803
698
  },
804
699
  "model": {
805
700
  "type": "string",
806
- "enum": [
807
- "sonnet"
808
- ],
701
+ "enum": ["sonnet"],
809
702
  "default": "sonnet",
810
703
  "description": "Cross-check model. Locked to Sonnet - Opus would just agree with Opus."
811
704
  },
@@ -864,10 +757,7 @@
864
757
  },
865
758
  "model": {
866
759
  "type": "string",
867
- "enum": [
868
- "sonnet",
869
- "opus"
870
- ],
760
+ "enum": ["sonnet", "opus"],
871
761
  "default": "sonnet",
872
762
  "description": "Verifier agent model. Writing a minimal repro test is mechanical work; Sonnet is the cost-sane default."
873
763
  },
@@ -904,11 +794,7 @@
904
794
  },
905
795
  "mode": {
906
796
  "type": "string",
907
- "enum": [
908
- "per-tool-call",
909
- "per-todo-step",
910
- "off"
911
- ],
797
+ "enum": ["per-tool-call", "per-todo-step", "off"],
912
798
  "default": "per-todo-step",
913
799
  "description": "Snapshot frequency. per-tool-call snapshots after each Edit/Write/Bash mutation; per-todo-step snapshots once per plan-todos.sh step boundary (cheaper, recommended). off is equivalent to enabled=false."
914
800
  },
@@ -945,10 +831,7 @@
945
831
  },
946
832
  "model": {
947
833
  "type": "string",
948
- "enum": [
949
- "haiku",
950
- "sonnet"
951
- ],
834
+ "enum": ["haiku", "sonnet"],
952
835
  "default": "haiku",
953
836
  "description": "Classifier model. Haiku is the cost default; Sonnet override for regulated domains where ambiguity nuance matters."
954
837
  },
@@ -968,11 +851,7 @@
968
851
  },
969
852
  "autopilotMode": {
970
853
  "type": "string",
971
- "enum": [
972
- "skip",
973
- "log",
974
- "abort"
975
- ],
854
+ "enum": ["skip", "log", "abort"],
976
855
  "default": "log",
977
856
  "description": "What to do when stopAndAsk fires in autopilot. skip = drop questions and proceed (most aggressive); log = append to agent-log.md and proceed (default, preserves signal); abort = pause Phase 0 and require multi-agent:resume."
978
857
  }
@@ -1015,21 +894,13 @@
1015
894
  },
1016
895
  "onExceed": {
1017
896
  "type": "string",
1018
- "enum": [
1019
- "warn",
1020
- "halt"
1021
- ],
897
+ "enum": ["warn", "halt"],
1022
898
  "default": "warn",
1023
899
  "description": "warn = surface the overage and continue (autopilot keeps going). halt = pause the run and require multi-agent:resume once the user accepts the cost. Interactive runs always surface the line regardless."
1024
900
  },
1025
901
  "pricingModel": {
1026
902
  "type": "string",
1027
- "enum": [
1028
- "fable",
1029
- "opus",
1030
- "sonnet",
1031
- "haiku"
1032
- ],
903
+ "enum": ["fable", "opus", "sonnet", "haiku"],
1033
904
  "default": "fable",
1034
905
  "description": "Which cost-table.json rate to price accumulated tokens at. Defaults to fable (the top tier since v10.6.0) for a deliberately conservative (upper-bound) estimate, so the ceiling trips early rather than late."
1035
906
  }
@@ -1120,11 +991,7 @@
1120
991
  },
1121
992
  "model": {
1122
993
  "type": "string",
1123
- "enum": [
1124
- "sonnet",
1125
- "opus",
1126
- "haiku"
1127
- ],
994
+ "enum": ["sonnet", "opus", "haiku"],
1128
995
  "default": "sonnet",
1129
996
  "description": "Critic model. Sonnet is the cost/quality default. Opus override only when diff > 500 LOC or touches security-critical paths. Haiku is too brittle for checklist reasoning - use only for trivial verification tasks."
1130
997
  },
@@ -1227,10 +1094,7 @@
1227
1094
  "description": "When true, also scan the repo tree (not just the diff) for existing tests that already mention the symbol - catches gaps that are technically covered by older tests outside the current diff. Slower but more accurate. Off by default - diff-only scan is sufficient for the common case."
1228
1095
  },
1229
1096
  "blockingThreshold": {
1230
- "type": [
1231
- "integer",
1232
- "null"
1233
- ],
1097
+ "type": ["integer", "null"],
1234
1098
  "minimum": 1,
1235
1099
  "default": null,
1236
1100
  "description": "If set, gaps where `important + blocking` count exceeds the threshold are treated as a Phase 4 rework finding (loops back to Phase 3). null = advisory only - Phase 5 prints the report but never gates."
@@ -1261,7 +1125,7 @@
1261
1125
  "dynamicSkillLoading": {
1262
1126
  "type": "boolean",
1263
1127
  "default": false,
1264
- "description": "v7.0.0+ - Dynamic trigger-based skill loading. When enabled, the orchestrator reads `~/.claude/skills/.skills-index.json` after Phase 1 analysis and injects only the top-N matched skills into subagent prompts (via `match-skills.mjs`), instead of relying on eager-loaded SKILL.md bodies. Large token win on small tasks; no visible behavior change on big ones where many skills match. Requires either a full install (index is always shipped) or the `install.js --index-only` mode for users who want skill bodies fetched on demand. Off by default in v7.0 - flip to `true` to opt in; a future v7.x may flip the default once enough telemetry confirms no regression."
1128
+ "description": "v7.0.0+ - Dynamic trigger-based skill loading. When enabled, the orchestrator reads `~/.claude/skills/.skills-index.json` after Phase 1 analysis and injects only the top-N matched skills into subagent prompts (via `match-skills.mjs`), instead of relying on eager-loaded SKILL.md bodies. Large token win on small tasks; no visible behavior change on big ones where many skills match. The index ships with every install - full and `--index-only` alike - so this is safe to flip on any installed tree. It was not always: until v13.6 only `--index-only` copied the index, and `match-skills.mjs` resolved its default index path relative to a repo checkout, so enabling this on a normal install produced `cannot read index` and a silent fall back to eager loading. Off by default - flip to `true` to opt in; a future release may flip the default once enough telemetry confirms no regression."
1265
1129
  },
1266
1130
  "derivedSkillSources": {
1267
1131
  "type": "array",
@@ -1269,12 +1133,7 @@
1269
1133
  "items": {
1270
1134
  "type": "object",
1271
1135
  "additionalProperties": false,
1272
- "required": [
1273
- "label",
1274
- "localPath",
1275
- "upstreamPlugin",
1276
- "derivedFromVersion"
1277
- ],
1136
+ "required": ["label", "localPath", "upstreamPlugin", "derivedFromVersion"],
1278
1137
  "properties": {
1279
1138
  "label": {
1280
1139
  "type": "string",
@@ -1304,10 +1163,7 @@
1304
1163
  "description": "Upstream version we last synced from, read from the manifest named by `upstreamVersionSource`. Bumped after a drift port is applied."
1305
1164
  },
1306
1165
  "upstreamVersionSource": {
1307
- "enum": [
1308
- "marketplace.json",
1309
- "plugin.json"
1310
- ],
1166
+ "enum": ["marketplace.json", "plugin.json"],
1311
1167
  "default": "marketplace.json",
1312
1168
  "description": "Which upstream manifest carries the authoritative version. Defaults to marketplace.json because that is what a marketplace consumer resolves; some upstreams keep plugin.json deliberately unused, so reading it silently records a version nobody ships. Recording from the wrong manifest is how an entry here sat at 0.7.0 while the marketplace said 0.6.0."
1313
1169
  },
@@ -1351,11 +1207,7 @@
1351
1207
  },
1352
1208
  "registry": {
1353
1209
  "type": "string",
1354
- "enum": [
1355
- "github-packages",
1356
- "npmjs",
1357
- "none"
1358
- ],
1210
+ "enum": ["github-packages", "npmjs", "none"],
1359
1211
  "default": "github-packages",
1360
1212
  "description": "Publish target for Step 3d. `none` means commit + push only, never publish. The concrete URL comes from the repo's publishConfig; the token comes from the `npm` logical Keychain key through a throwaway --userconfig."
1361
1213
  },
@@ -1371,9 +1223,7 @@
1371
1223
  "items": {
1372
1224
  "type": "object",
1373
1225
  "additionalProperties": false,
1374
- "required": [
1375
- "id"
1376
- ],
1226
+ "required": ["id"],
1377
1227
  "properties": {
1378
1228
  "id": {
1379
1229
  "type": "string",
@@ -1401,9 +1251,7 @@
1401
1251
  "items": {
1402
1252
  "type": "object",
1403
1253
  "additionalProperties": false,
1404
- "required": [
1405
- "id"
1406
- ],
1254
+ "required": ["id"],
1407
1255
  "properties": {
1408
1256
  "id": {
1409
1257
  "type": "string",
@@ -1426,16 +1274,35 @@
1426
1274
  },
1427
1275
  "defaultProvider": {
1428
1276
  "type": "string",
1429
- "enum": [
1430
- "github",
1431
- "bitbucket",
1432
- "gitlab",
1433
- "generic-git"
1434
- ]
1277
+ "enum": ["github", "bitbucket", "gitlab", "generic-git"]
1435
1278
  }
1436
1279
  }
1437
1280
  },
1438
1281
  "maxItems": 20
1282
+ },
1283
+ "skillConformance": {
1284
+ "type": "object",
1285
+ "additionalProperties": false,
1286
+ "description": "v14.0.0+ - Phase 4 Step 1.78 criteria resolution. The stage itself has no on/off key and neither does its exception-expiry check: a run that can switch off its own anti-reward-hacking control cannot be trusted to report a pass (same reasoning as Step 1.76).",
1287
+ "properties": {
1288
+ "blockOnCoverageGap": {
1289
+ "type": "boolean",
1290
+ "default": false,
1291
+ "description": "Whether a declared coverage gap halts the run. A gap means a language in the diff that no rule registry covers, and it is REPORTED either way - this key only decides whether it also stops the pipeline. Default false because only Swift plus the two store-compliance catalogs ship a scoped registry today, so defaulting true would block every Kotlin, Python, Node and Objective-C run on day one. Flip to true once your stack's registry exists and you want an uncovered file treated as a failure rather than a note."
1292
+ }
1293
+ }
1294
+ },
1295
+ "ship": {
1296
+ "type": "object",
1297
+ "additionalProperties": false,
1298
+ "description": "v14.0.0+ - /multi-agent:ship (formerly :finish), the tail that runs review + build/test + PR + report over work already on the branch.",
1299
+ "properties": {
1300
+ "autoFix": {
1301
+ "type": "boolean",
1302
+ "default": false,
1303
+ "description": "When true, ship auto-fixes triage-accepted blocking/important findings and re-reviews instead of asking. Equivalent to passing `autopilot` on every run. Default false: ship operates on work the user wrote by hand, so silently rewriting it is the surprising option."
1304
+ }
1305
+ }
1439
1306
  }
1440
1307
  }
1441
1308
  },
@@ -1465,10 +1332,7 @@
1465
1332
  },
1466
1333
  "defaultPrMode": {
1467
1334
  "type": "string",
1468
- "enum": [
1469
- "draft",
1470
- "ready"
1471
- ],
1335
+ "enum": ["draft", "ready"],
1472
1336
  "description": "Last-used draft/ready choice, shown as the default on next prompt."
1473
1337
  },
1474
1338
  "baseBranch": {
@@ -1507,12 +1371,7 @@
1507
1371
  },
1508
1372
  "remoteType": {
1509
1373
  "type": "string",
1510
- "enum": [
1511
- "bitbucket",
1512
- "github",
1513
- "gitlab",
1514
- "generic-git"
1515
- ],
1374
+ "enum": ["bitbucket", "github", "gitlab", "generic-git"],
1516
1375
  "description": "Hint used when repo URL doesn't make platform obvious."
1517
1376
  },
1518
1377
  "taskCount": {
@@ -1566,10 +1425,7 @@
1566
1425
  "description": "Per-project App Store Connect delivery settings. Per-project rather than global because a user can ship for more than one team.",
1567
1426
  "properties": {
1568
1427
  "providerPublicId": {
1569
- "type": [
1570
- "string",
1571
- "null"
1572
- ],
1428
+ "type": ["string", "null"],
1573
1429
  "description": "Provider (team) public ID, required by altool when the account belongs to several providers. Resolve once with ios_testflight_validate({list_providers:true}); without it altool fails opaquely."
1574
1430
  }
1575
1431
  }