@harness-engineering/cli 1.9.0 → 1.10.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.
- package/dist/agents/skills/claude-code/harness-autopilot/SKILL.md +7 -2
- package/dist/agents/skills/claude-code/harness-brainstorming/SKILL.md +10 -1
- package/dist/agents/skills/claude-code/harness-execution/SKILL.md +2 -2
- package/dist/agents/skills/gemini-cli/harness-autopilot/SKILL.md +7 -2
- package/dist/agents/skills/gemini-cli/harness-brainstorming/SKILL.md +10 -1
- package/dist/agents/skills/gemini-cli/harness-execution/SKILL.md +2 -2
- package/dist/agents-md-EMRFLNBC.js +8 -0
- package/dist/architecture-5JNN5L3M.js +13 -0
- package/dist/bin/harness-mcp.d.ts +1 -0
- package/dist/bin/harness-mcp.js +28 -0
- package/dist/bin/harness.js +42 -8
- package/dist/check-phase-gate-WOKIYGAM.js +12 -0
- package/dist/chunk-46YA6FI3.js +293 -0
- package/dist/chunk-4PFMY3H7.js +248 -0
- package/dist/{chunk-6JIT7CEM.js → chunk-72GHBOL2.js} +1 -1
- package/dist/chunk-7X7ZAYMY.js +373 -0
- package/dist/chunk-B7HFEHWP.js +35 -0
- package/dist/chunk-BM3PWGXQ.js +14 -0
- package/dist/chunk-C2ERUR3L.js +255 -0
- package/dist/chunk-CWZ4Y2PO.js +189 -0
- package/dist/{chunk-ULSRSP53.js → chunk-ECUJQS3B.js} +11 -112
- package/dist/chunk-EOLRW32Q.js +72 -0
- package/dist/chunk-F3YDAJFQ.js +125 -0
- package/dist/chunk-F4PTVZWA.js +116 -0
- package/dist/chunk-FPIPT36X.js +187 -0
- package/dist/chunk-FX7SQHGD.js +103 -0
- package/dist/chunk-HIOXKZYF.js +15 -0
- package/dist/chunk-IDZNPTYD.js +16 -0
- package/dist/chunk-JSTQ3AWB.js +31 -0
- package/dist/chunk-K6XAPGML.js +27 -0
- package/dist/chunk-KET4QQZB.js +8 -0
- package/dist/chunk-LXU5M77O.js +4028 -0
- package/dist/chunk-MDUK2J2O.js +67 -0
- package/dist/chunk-MHBMTPW7.js +29 -0
- package/dist/chunk-MO4YQOMB.js +85 -0
- package/dist/chunk-NKDM3FMH.js +52 -0
- package/dist/{chunk-CGSHUJES.js → chunk-NX6DSZSM.js} +7 -26
- package/dist/chunk-OPXH4CQN.js +62 -0
- package/dist/{chunk-RTPHUDZS.js → chunk-PAHHT2IK.js} +466 -2714
- package/dist/chunk-PMTFPOCT.js +122 -0
- package/dist/chunk-PSXF277V.js +89 -0
- package/dist/chunk-Q6AB7W5Z.js +135 -0
- package/dist/chunk-QPEH2QPG.js +347 -0
- package/dist/chunk-TEFCFC4H.js +15 -0
- package/dist/chunk-TRAPF4IX.js +185 -0
- package/dist/chunk-VUCPTQ6G.js +67 -0
- package/dist/chunk-W6Y7ZW3Y.js +13 -0
- package/dist/chunk-ZOAWBDWU.js +72 -0
- package/dist/ci-workflow-ZBBUNTHQ.js +8 -0
- package/dist/constants-5JGUXPEK.js +6 -0
- package/dist/create-skill-LUWO46WF.js +11 -0
- package/dist/dist-D4RYGUZE.js +14 -0
- package/dist/dist-L7LAAQAS.js +18 -0
- package/dist/{dist-C5PYIQPF.js → dist-PBTNVK6K.js} +8 -6
- package/dist/docs-PTJGD6XI.js +12 -0
- package/dist/engine-SCMZ3G3E.js +8 -0
- package/dist/entropy-YIUBGKY7.js +12 -0
- package/dist/feedback-WEVQSLAA.js +18 -0
- package/dist/generate-agent-definitions-BU5LOJTI.js +15 -0
- package/dist/glob-helper-5OHBUQAI.js +52 -0
- package/dist/graph-loader-RLO3KRIX.js +8 -0
- package/dist/index.d.ts +11 -1
- package/dist/index.js +84 -33
- package/dist/loader-6S6PVGSF.js +10 -0
- package/dist/mcp-BNLBTCXZ.js +34 -0
- package/dist/performance-5TVW6SA6.js +24 -0
- package/dist/review-pipeline-4JTQAWKW.js +9 -0
- package/dist/runner-VMYLHWOC.js +6 -0
- package/dist/runtime-PXIM7UV6.js +9 -0
- package/dist/security-URYTKLGK.js +9 -0
- package/dist/skill-executor-KVS47DAU.js +8 -0
- package/dist/validate-KSDUUK2M.js +12 -0
- package/dist/validate-cross-check-WZAX357V.js +8 -0
- package/dist/version-KFFPOQAX.js +6 -0
- package/package.json +6 -4
- package/dist/create-skill-UZOHMXRU.js +0 -8
- package/dist/validate-cross-check-VG573VZO.js +0 -7
|
@@ -339,7 +339,9 @@ INIT → ASSESS → PLAN → APPROVE_PLAN → EXECUTE → VERIFY → REVIEW →
|
|
|
339
339
|
|
|
340
340
|
3. **Mark phase as `complete`** in state.
|
|
341
341
|
|
|
342
|
-
4. **
|
|
342
|
+
4. **Sync roadmap.** If `docs/roadmap.md` exists, call `manage_roadmap` with action `sync` and `apply: true`. This reflects the just-completed phase in the roadmap (e.g., updating the feature from `planned` to `in-progress`). If `manage_roadmap` is unavailable, fall back to direct file manipulation using `syncRoadmap()` from core. Skip silently if no roadmap exists. Do not use `force_sync: true` — the human-always-wins rule applies.
|
|
343
|
+
|
|
344
|
+
5. **Check for next phase:**
|
|
343
345
|
- If more phases remain: "Phase {N} complete. Next: Phase {N+1}: {name} (complexity: {level}). Continue? (yes / stop)"
|
|
344
346
|
- **yes** — Increment `currentPhase`, reset `retryBudget`, transition to ASSESS.
|
|
345
347
|
- **stop** — Save state and exit.
|
|
@@ -383,7 +385,9 @@ INIT → ASSESS → PLAN → APPROVE_PLAN → EXECUTE → VERIFY → REVIEW →
|
|
|
383
385
|
- [skill:harness-autopilot] [outcome:observation] {any notable patterns from the run}
|
|
384
386
|
```
|
|
385
387
|
|
|
386
|
-
5. **
|
|
388
|
+
5. **Update roadmap to done.** If `docs/roadmap.md` exists and the current spec maps to a roadmap feature, call `manage_roadmap` with action `update` to set the feature status to `done`. Derive the feature name from the spec title (H1 heading) or the session's `handoff.json` `summary` field. If `manage_roadmap` is unavailable, fall back to direct file manipulation using `updateFeature()` from core. Skip silently if no roadmap exists or if the feature is not found. Do not use `force_sync: true`.
|
|
389
|
+
|
|
390
|
+
6. **Clean up state:** Set `currentState: "DONE"` in `{sessionDir}/autopilot-state.json`. Do not delete the file — it serves as a record.
|
|
387
391
|
|
|
388
392
|
## Harness Integration
|
|
389
393
|
|
|
@@ -394,6 +398,7 @@ INIT → ASSESS → PLAN → APPROVE_PLAN → EXECUTE → VERIFY → REVIEW →
|
|
|
394
398
|
- **Handoff** — `.harness/sessions/<slug>/handoff.json` is written by each delegated skill and read by the next. Autopilot writes a final handoff on DONE.
|
|
395
399
|
- **Learnings** — `.harness/learnings.md` (global) is appended by both delegated skills and autopilot itself.
|
|
396
400
|
- **Roadmap context** — During INIT, reads `docs/roadmap.md` (if present) for project-level priorities, blockers, and milestone status. Provides broader context for phase execution decisions.
|
|
401
|
+
- **Roadmap sync** — During PHASE_COMPLETE, calls `manage_roadmap` with `sync` and `apply: true` to reflect phase progress. During DONE, calls `manage_roadmap` with `update` to set feature status to `done`. Both skip silently when no roadmap exists. Neither uses `force_sync: true`.
|
|
397
402
|
|
|
398
403
|
## Success Criteria
|
|
399
404
|
|
|
@@ -156,7 +156,15 @@ These keywords flow into the `handoff.json` `contextKeywords` field when the spe
|
|
|
156
156
|
|
|
157
157
|
The human must explicitly approve before this skill is complete.
|
|
158
158
|
|
|
159
|
-
6. **
|
|
159
|
+
6. **Add feature to roadmap.** If `docs/roadmap.md` exists:
|
|
160
|
+
- Derive the feature name from the spec title (the H1 heading of the proposal).
|
|
161
|
+
- Call `manage_roadmap` with action `add`, `status: "planned"`, `milestone: "Current Work"`, and the spec path. Include a one-line summary from the spec overview.
|
|
162
|
+
- If the feature already exists in the roadmap (duplicate name), skip silently — the feature was likely added manually or by a prior brainstorming session.
|
|
163
|
+
- Log: `"Added '<feature-name>' to roadmap as planned"` (informational, not a prompt).
|
|
164
|
+
- If `manage_roadmap` is unavailable, fall back to direct file manipulation using `addFeature()` from core.
|
|
165
|
+
- If no roadmap exists, skip this step silently.
|
|
166
|
+
|
|
167
|
+
7. **Write handoff and suggest transition.** After the human approves the spec:
|
|
160
168
|
|
|
161
169
|
Write `.harness/handoff.json`:
|
|
162
170
|
|
|
@@ -257,6 +265,7 @@ Converge on a recommendation that addresses all concerns before presenting the d
|
|
|
257
265
|
- **`harness check-docs`** — Run to verify the spec does not conflict with existing documentation.
|
|
258
266
|
- **Spec location** — Specs go to `docs/changes/<feature>/proposal.md`. Follow existing naming patterns.
|
|
259
267
|
- **Handoff to harness-planning** — Once the spec is approved, invoke harness-planning to create the implementation plan from the spec.
|
|
268
|
+
- **Roadmap sync** — After spec approval, call `manage_roadmap` with action `add` to register the new feature as `planned` in `docs/roadmap.md`. Skip silently if no roadmap exists. Duplicates are silently ignored.
|
|
260
269
|
- **`emit_interaction`** -- Call at the end of Phase 4 to suggest transitioning to harness-planning. Uses confirmed transition (waits for user approval).
|
|
261
270
|
|
|
262
271
|
#### Requirement Phrasing
|
|
@@ -266,7 +266,7 @@ Skipping this step means subsequent graph queries (impact analysis, dependency h
|
|
|
266
266
|
}
|
|
267
267
|
```
|
|
268
268
|
|
|
269
|
-
5. **Sync roadmap (
|
|
269
|
+
5. **Sync roadmap (mandatory when present).** If `docs/roadmap.md` exists, call `manage_roadmap` with action `sync` and `apply: true` to update linked feature statuses from the just-completed execution state. Do not use `force_sync: true` — the human-always-wins rule applies. If `manage_roadmap` is unavailable, fall back to direct file manipulation using `syncRoadmap()` from core. If no roadmap exists, skip silently.
|
|
270
270
|
|
|
271
271
|
6. **Learnings are append-only.** Never edit or delete previous learnings. They are a chronological record.
|
|
272
272
|
|
|
@@ -327,7 +327,7 @@ These are non-negotiable. When any condition is met, stop immediately.
|
|
|
327
327
|
- **`harness state learn "<message>"`** — Append a learning from the command line.
|
|
328
328
|
- **`.harness/state.json`** — Read at session start to resume position. Updated after every task.
|
|
329
329
|
- **`.harness/learnings.md`** — Append-only knowledge capture. Read at session start for prior context.
|
|
330
|
-
- **Roadmap sync** — After completing plan execution,
|
|
330
|
+
- **Roadmap sync** — After completing plan execution, call `manage_roadmap` with action `sync` and `apply: true` to update roadmap status. Mandatory when `docs/roadmap.md` exists. Do not use `force_sync: true`. Falls back to `syncRoadmap()` from core if MCP tool is unavailable.
|
|
331
331
|
- **`emit_interaction`** -- Call at plan completion to auto-transition to harness-verification. Uses auto-transition (proceeds immediately without user confirmation).
|
|
332
332
|
|
|
333
333
|
## Success Criteria
|
|
@@ -339,7 +339,9 @@ INIT → ASSESS → PLAN → APPROVE_PLAN → EXECUTE → VERIFY → REVIEW →
|
|
|
339
339
|
|
|
340
340
|
3. **Mark phase as `complete`** in state.
|
|
341
341
|
|
|
342
|
-
4. **
|
|
342
|
+
4. **Sync roadmap.** If `docs/roadmap.md` exists, call `manage_roadmap` with action `sync` and `apply: true`. This reflects the just-completed phase in the roadmap (e.g., updating the feature from `planned` to `in-progress`). If `manage_roadmap` is unavailable, fall back to direct file manipulation using `syncRoadmap()` from core. Skip silently if no roadmap exists. Do not use `force_sync: true` — the human-always-wins rule applies.
|
|
343
|
+
|
|
344
|
+
5. **Check for next phase:**
|
|
343
345
|
- If more phases remain: "Phase {N} complete. Next: Phase {N+1}: {name} (complexity: {level}). Continue? (yes / stop)"
|
|
344
346
|
- **yes** — Increment `currentPhase`, reset `retryBudget`, transition to ASSESS.
|
|
345
347
|
- **stop** — Save state and exit.
|
|
@@ -383,7 +385,9 @@ INIT → ASSESS → PLAN → APPROVE_PLAN → EXECUTE → VERIFY → REVIEW →
|
|
|
383
385
|
- [skill:harness-autopilot] [outcome:observation] {any notable patterns from the run}
|
|
384
386
|
```
|
|
385
387
|
|
|
386
|
-
5. **
|
|
388
|
+
5. **Update roadmap to done.** If `docs/roadmap.md` exists and the current spec maps to a roadmap feature, call `manage_roadmap` with action `update` to set the feature status to `done`. Derive the feature name from the spec title (H1 heading) or the session's `handoff.json` `summary` field. If `manage_roadmap` is unavailable, fall back to direct file manipulation using `updateFeature()` from core. Skip silently if no roadmap exists or if the feature is not found. Do not use `force_sync: true`.
|
|
389
|
+
|
|
390
|
+
6. **Clean up state:** Set `currentState: "DONE"` in `{sessionDir}/autopilot-state.json`. Do not delete the file — it serves as a record.
|
|
387
391
|
|
|
388
392
|
## Harness Integration
|
|
389
393
|
|
|
@@ -394,6 +398,7 @@ INIT → ASSESS → PLAN → APPROVE_PLAN → EXECUTE → VERIFY → REVIEW →
|
|
|
394
398
|
- **Handoff** — `.harness/sessions/<slug>/handoff.json` is written by each delegated skill and read by the next. Autopilot writes a final handoff on DONE.
|
|
395
399
|
- **Learnings** — `.harness/learnings.md` (global) is appended by both delegated skills and autopilot itself.
|
|
396
400
|
- **Roadmap context** — During INIT, reads `docs/roadmap.md` (if present) for project-level priorities, blockers, and milestone status. Provides broader context for phase execution decisions.
|
|
401
|
+
- **Roadmap sync** — During PHASE_COMPLETE, calls `manage_roadmap` with `sync` and `apply: true` to reflect phase progress. During DONE, calls `manage_roadmap` with `update` to set feature status to `done`. Both skip silently when no roadmap exists. Neither uses `force_sync: true`.
|
|
397
402
|
|
|
398
403
|
## Success Criteria
|
|
399
404
|
|
|
@@ -156,7 +156,15 @@ These keywords flow into the `handoff.json` `contextKeywords` field when the spe
|
|
|
156
156
|
|
|
157
157
|
The human must explicitly approve before this skill is complete.
|
|
158
158
|
|
|
159
|
-
6. **
|
|
159
|
+
6. **Add feature to roadmap.** If `docs/roadmap.md` exists:
|
|
160
|
+
- Derive the feature name from the spec title (the H1 heading of the proposal).
|
|
161
|
+
- Call `manage_roadmap` with action `add`, `status: "planned"`, `milestone: "Current Work"`, and the spec path. Include a one-line summary from the spec overview.
|
|
162
|
+
- If the feature already exists in the roadmap (duplicate name), skip silently — the feature was likely added manually or by a prior brainstorming session.
|
|
163
|
+
- Log: `"Added '<feature-name>' to roadmap as planned"` (informational, not a prompt).
|
|
164
|
+
- If `manage_roadmap` is unavailable, fall back to direct file manipulation using `addFeature()` from core.
|
|
165
|
+
- If no roadmap exists, skip this step silently.
|
|
166
|
+
|
|
167
|
+
7. **Write handoff and suggest transition.** After the human approves the spec:
|
|
160
168
|
|
|
161
169
|
Write `.harness/handoff.json`:
|
|
162
170
|
|
|
@@ -257,6 +265,7 @@ Converge on a recommendation that addresses all concerns before presenting the d
|
|
|
257
265
|
- **`harness check-docs`** — Run to verify the spec does not conflict with existing documentation.
|
|
258
266
|
- **Spec location** — Specs go to `docs/changes/<feature>/proposal.md`. Follow existing naming patterns.
|
|
259
267
|
- **Handoff to harness-planning** — Once the spec is approved, invoke harness-planning to create the implementation plan from the spec.
|
|
268
|
+
- **Roadmap sync** — After spec approval, call `manage_roadmap` with action `add` to register the new feature as `planned` in `docs/roadmap.md`. Skip silently if no roadmap exists. Duplicates are silently ignored.
|
|
260
269
|
- **`emit_interaction`** -- Call at the end of Phase 4 to suggest transitioning to harness-planning. Uses confirmed transition (waits for user approval).
|
|
261
270
|
|
|
262
271
|
#### Requirement Phrasing
|
|
@@ -266,7 +266,7 @@ Skipping this step means subsequent graph queries (impact analysis, dependency h
|
|
|
266
266
|
}
|
|
267
267
|
```
|
|
268
268
|
|
|
269
|
-
5. **Sync roadmap (
|
|
269
|
+
5. **Sync roadmap (mandatory when present).** If `docs/roadmap.md` exists, call `manage_roadmap` with action `sync` and `apply: true` to update linked feature statuses from the just-completed execution state. Do not use `force_sync: true` — the human-always-wins rule applies. If `manage_roadmap` is unavailable, fall back to direct file manipulation using `syncRoadmap()` from core. If no roadmap exists, skip silently.
|
|
270
270
|
|
|
271
271
|
6. **Learnings are append-only.** Never edit or delete previous learnings. They are a chronological record.
|
|
272
272
|
|
|
@@ -327,7 +327,7 @@ These are non-negotiable. When any condition is met, stop immediately.
|
|
|
327
327
|
- **`harness state learn "<message>"`** — Append a learning from the command line.
|
|
328
328
|
- **`.harness/state.json`** — Read at session start to resume position. Updated after every task.
|
|
329
329
|
- **`.harness/learnings.md`** — Append-only knowledge capture. Read at session start for prior context.
|
|
330
|
-
- **Roadmap sync** — After completing plan execution,
|
|
330
|
+
- **Roadmap sync** — After completing plan execution, call `manage_roadmap` with action `sync` and `apply: true` to update roadmap status. Mandatory when `docs/roadmap.md` exists. Do not use `force_sync: true`. Falls back to `syncRoadmap()` from core if MCP tool is unavailable.
|
|
331
331
|
- **`emit_interaction`** -- Call at plan completion to auto-transition to harness-verification. Uses auto-transition (proceeds immediately without user confirmation).
|
|
332
332
|
|
|
333
333
|
## Success Criteria
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import {
|
|
2
|
+
checkDependenciesDefinition,
|
|
3
|
+
handleCheckDependencies
|
|
4
|
+
} from "./chunk-MO4YQOMB.js";
|
|
5
|
+
import "./chunk-K6XAPGML.js";
|
|
6
|
+
import "./chunk-IDZNPTYD.js";
|
|
7
|
+
import "./chunk-W6Y7ZW3Y.js";
|
|
8
|
+
import "./chunk-NX6DSZSM.js";
|
|
9
|
+
import "./chunk-MHBMTPW7.js";
|
|
10
|
+
export {
|
|
11
|
+
checkDependenciesDefinition,
|
|
12
|
+
handleCheckDependencies
|
|
13
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import {
|
|
3
|
+
startServer
|
|
4
|
+
} from "../chunk-LXU5M77O.js";
|
|
5
|
+
import "../chunk-CWZ4Y2PO.js";
|
|
6
|
+
import "../chunk-FPIPT36X.js";
|
|
7
|
+
import "../chunk-4PFMY3H7.js";
|
|
8
|
+
import "../chunk-PSXF277V.js";
|
|
9
|
+
import "../chunk-PMTFPOCT.js";
|
|
10
|
+
import "../chunk-ZOAWBDWU.js";
|
|
11
|
+
import "../chunk-FX7SQHGD.js";
|
|
12
|
+
import "../chunk-OPXH4CQN.js";
|
|
13
|
+
import "../chunk-MO4YQOMB.js";
|
|
14
|
+
import "../chunk-K6XAPGML.js";
|
|
15
|
+
import "../chunk-F4PTVZWA.js";
|
|
16
|
+
import "../chunk-IDZNPTYD.js";
|
|
17
|
+
import "../chunk-W6Y7ZW3Y.js";
|
|
18
|
+
import "../chunk-EOLRW32Q.js";
|
|
19
|
+
import "../chunk-B7HFEHWP.js";
|
|
20
|
+
import "../chunk-MDUK2J2O.js";
|
|
21
|
+
import "../chunk-NX6DSZSM.js";
|
|
22
|
+
import "../chunk-MHBMTPW7.js";
|
|
23
|
+
|
|
24
|
+
// src/bin/harness-mcp.ts
|
|
25
|
+
startServer().catch((error) => {
|
|
26
|
+
console.error("Failed to start MCP server:", error);
|
|
27
|
+
process.exit(1);
|
|
28
|
+
});
|
package/dist/bin/harness.js
CHANGED
|
@@ -1,21 +1,55 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
|
-
|
|
4
|
-
|
|
3
|
+
createProgram
|
|
4
|
+
} from "../chunk-PAHHT2IK.js";
|
|
5
|
+
import "../chunk-VUCPTQ6G.js";
|
|
6
|
+
import {
|
|
5
7
|
findConfigFile,
|
|
6
8
|
loadConfig
|
|
7
|
-
} from "../chunk-
|
|
8
|
-
import "../chunk-
|
|
9
|
+
} from "../chunk-7X7ZAYMY.js";
|
|
10
|
+
import "../chunk-46YA6FI3.js";
|
|
11
|
+
import "../chunk-Q6AB7W5Z.js";
|
|
12
|
+
import "../chunk-TRAPF4IX.js";
|
|
13
|
+
import "../chunk-F3YDAJFQ.js";
|
|
14
|
+
import "../chunk-TEFCFC4H.js";
|
|
15
|
+
import "../chunk-ECUJQS3B.js";
|
|
16
|
+
import "../chunk-HIOXKZYF.js";
|
|
17
|
+
import "../chunk-QPEH2QPG.js";
|
|
18
|
+
import "../chunk-JSTQ3AWB.js";
|
|
19
|
+
import "../chunk-KET4QQZB.js";
|
|
20
|
+
import "../chunk-NKDM3FMH.js";
|
|
21
|
+
import "../chunk-LXU5M77O.js";
|
|
22
|
+
import "../chunk-CWZ4Y2PO.js";
|
|
23
|
+
import "../chunk-FPIPT36X.js";
|
|
24
|
+
import "../chunk-4PFMY3H7.js";
|
|
25
|
+
import "../chunk-PSXF277V.js";
|
|
26
|
+
import "../chunk-PMTFPOCT.js";
|
|
27
|
+
import "../chunk-ZOAWBDWU.js";
|
|
28
|
+
import "../chunk-FX7SQHGD.js";
|
|
29
|
+
import "../chunk-OPXH4CQN.js";
|
|
30
|
+
import "../chunk-MO4YQOMB.js";
|
|
31
|
+
import "../chunk-K6XAPGML.js";
|
|
32
|
+
import "../chunk-F4PTVZWA.js";
|
|
33
|
+
import "../chunk-IDZNPTYD.js";
|
|
34
|
+
import "../chunk-W6Y7ZW3Y.js";
|
|
35
|
+
import "../chunk-EOLRW32Q.js";
|
|
36
|
+
import {
|
|
37
|
+
handleError
|
|
38
|
+
} from "../chunk-B7HFEHWP.js";
|
|
39
|
+
import "../chunk-MDUK2J2O.js";
|
|
40
|
+
import {
|
|
41
|
+
CLI_VERSION
|
|
42
|
+
} from "../chunk-BM3PWGXQ.js";
|
|
43
|
+
import "../chunk-72GHBOL2.js";
|
|
44
|
+
import "../chunk-C2ERUR3L.js";
|
|
9
45
|
import {
|
|
10
46
|
getUpdateNotification,
|
|
11
47
|
isUpdateCheckEnabled,
|
|
12
48
|
readCheckState,
|
|
13
49
|
shouldRunCheck,
|
|
14
50
|
spawnBackgroundCheck
|
|
15
|
-
} from "../chunk-
|
|
16
|
-
import
|
|
17
|
-
handleError
|
|
18
|
-
} from "../chunk-ULSRSP53.js";
|
|
51
|
+
} from "../chunk-NX6DSZSM.js";
|
|
52
|
+
import "../chunk-MHBMTPW7.js";
|
|
19
53
|
|
|
20
54
|
// src/bin/update-check-hooks.ts
|
|
21
55
|
var DEFAULT_INTERVAL_MS = 864e5;
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import {
|
|
2
|
+
createCheckPhaseGateCommand,
|
|
3
|
+
runCheckPhaseGate
|
|
4
|
+
} from "./chunk-7X7ZAYMY.js";
|
|
5
|
+
import "./chunk-HIOXKZYF.js";
|
|
6
|
+
import "./chunk-B7HFEHWP.js";
|
|
7
|
+
import "./chunk-NX6DSZSM.js";
|
|
8
|
+
import "./chunk-MHBMTPW7.js";
|
|
9
|
+
export {
|
|
10
|
+
createCheckPhaseGateCommand,
|
|
11
|
+
runCheckPhaseGate
|
|
12
|
+
};
|
|
@@ -0,0 +1,293 @@
|
|
|
1
|
+
import {
|
|
2
|
+
listPersonas,
|
|
3
|
+
loadPersona
|
|
4
|
+
} from "./chunk-Q6AB7W5Z.js";
|
|
5
|
+
import {
|
|
6
|
+
toKebabCase
|
|
7
|
+
} from "./chunk-KET4QQZB.js";
|
|
8
|
+
import {
|
|
9
|
+
GENERATED_HEADER_AGENT,
|
|
10
|
+
VALID_PLATFORMS,
|
|
11
|
+
applySyncPlan,
|
|
12
|
+
computeSyncPlan
|
|
13
|
+
} from "./chunk-ZOAWBDWU.js";
|
|
14
|
+
import {
|
|
15
|
+
resolvePersonasDir,
|
|
16
|
+
resolveSkillsDir
|
|
17
|
+
} from "./chunk-EOLRW32Q.js";
|
|
18
|
+
import {
|
|
19
|
+
CLIError,
|
|
20
|
+
ExitCode,
|
|
21
|
+
handleError
|
|
22
|
+
} from "./chunk-B7HFEHWP.js";
|
|
23
|
+
|
|
24
|
+
// src/commands/generate-agent-definitions.ts
|
|
25
|
+
import { Command } from "commander";
|
|
26
|
+
import * as fs from "fs";
|
|
27
|
+
import * as path from "path";
|
|
28
|
+
import * as os from "os";
|
|
29
|
+
|
|
30
|
+
// src/agent-definitions/generator.ts
|
|
31
|
+
var AGENT_DESCRIPTIONS = {
|
|
32
|
+
"code-reviewer": "Perform code review and address review findings using harness methodology. Use when reviewing code, fixing review findings, responding to review feedback, or when a code review has produced issues that need to be addressed.",
|
|
33
|
+
"task-executor": "Execute implementation plans task-by-task with state tracking, TDD, and verification. Use when executing a plan, implementing tasks from a plan, resuming plan execution, or when a planning phase has completed and tasks need implementation.",
|
|
34
|
+
"parallel-coordinator": "Dispatch independent tasks across isolated agents for parallel execution. Use when multiple independent tasks need to run concurrently, splitting work across agents, or coordinating parallel implementation.",
|
|
35
|
+
"architecture-enforcer": "Validate architectural constraints and dependency rules. Use when checking layer boundaries, detecting circular dependencies, or verifying import direction compliance.",
|
|
36
|
+
"documentation-maintainer": "Keep documentation in sync with source code. Use when detecting documentation drift, validating doc coverage, or aligning docs with code changes.",
|
|
37
|
+
"entropy-cleaner": "Detect and fix codebase entropy including drift, dead code, and pattern violations. Use when running cleanup, detecting dead code, or fixing pattern violations.",
|
|
38
|
+
planner: "Create detailed implementation plans from specs with task breakdown, dependency ordering, and checkpoint placement. Use when planning a phase, breaking a spec into tasks, or creating an execution plan.",
|
|
39
|
+
verifier: "Verify implementation completeness against spec and plan at three tiers (EXISTS, SUBSTANTIVE, WIRED). Use when checking if built code matches what was planned, validating phase completion, or auditing implementation quality."
|
|
40
|
+
};
|
|
41
|
+
var DEFAULT_TOOLS = ["Bash", "Read", "Write", "Edit", "Glob", "Grep"];
|
|
42
|
+
var GEMINI_TOOL_MAP = {
|
|
43
|
+
Bash: "run_shell_command",
|
|
44
|
+
Read: "read_file",
|
|
45
|
+
Write: "write_file",
|
|
46
|
+
Edit: "replace",
|
|
47
|
+
Glob: "glob",
|
|
48
|
+
Grep: "search_file_content"
|
|
49
|
+
};
|
|
50
|
+
function generateAgentDefinition(persona, skillContents) {
|
|
51
|
+
const kebabName = toKebabCase(persona.name);
|
|
52
|
+
const name = `harness-${kebabName}`;
|
|
53
|
+
const description = AGENT_DESCRIPTIONS[kebabName] ?? persona.description;
|
|
54
|
+
const methodologyParts = [];
|
|
55
|
+
for (const skillName of persona.skills) {
|
|
56
|
+
const content = skillContents.get(skillName);
|
|
57
|
+
if (content) {
|
|
58
|
+
methodologyParts.push(content);
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
return {
|
|
62
|
+
name,
|
|
63
|
+
description,
|
|
64
|
+
tools: [...DEFAULT_TOOLS],
|
|
65
|
+
role: persona.role,
|
|
66
|
+
skills: persona.skills,
|
|
67
|
+
steps: persona.steps,
|
|
68
|
+
methodology: methodologyParts.join("\n\n---\n\n")
|
|
69
|
+
};
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
// src/agent-definitions/render-claude-code.ts
|
|
73
|
+
function formatStep(step, index) {
|
|
74
|
+
if ("command" in step && step.command) {
|
|
75
|
+
const cmd = step.command;
|
|
76
|
+
const when = step.when ?? "always";
|
|
77
|
+
return `${index + 1}. Run \`harness ${cmd}\` (${when})`;
|
|
78
|
+
}
|
|
79
|
+
if ("skill" in step && step.skill) {
|
|
80
|
+
const skill = step.skill;
|
|
81
|
+
const when = step.when ?? "always";
|
|
82
|
+
return `${index + 1}. Execute ${skill} skill (${when})`;
|
|
83
|
+
}
|
|
84
|
+
return `${index + 1}. Unknown step`;
|
|
85
|
+
}
|
|
86
|
+
function renderClaudeCodeAgent(def) {
|
|
87
|
+
const lines = ["---"];
|
|
88
|
+
lines.push(`name: ${def.name}`);
|
|
89
|
+
lines.push(`description: >`);
|
|
90
|
+
lines.push(` ${def.description}`);
|
|
91
|
+
lines.push(`tools: ${def.tools.join(", ")}`);
|
|
92
|
+
lines.push("---");
|
|
93
|
+
lines.push("");
|
|
94
|
+
lines.push(GENERATED_HEADER_AGENT);
|
|
95
|
+
lines.push("");
|
|
96
|
+
lines.push("## Role");
|
|
97
|
+
lines.push("");
|
|
98
|
+
lines.push(def.role);
|
|
99
|
+
lines.push("");
|
|
100
|
+
lines.push("## Skills");
|
|
101
|
+
lines.push("");
|
|
102
|
+
for (const skill of def.skills) {
|
|
103
|
+
lines.push(`- ${skill}`);
|
|
104
|
+
}
|
|
105
|
+
lines.push("");
|
|
106
|
+
lines.push("## Steps");
|
|
107
|
+
lines.push("");
|
|
108
|
+
def.steps.forEach((step, i) => {
|
|
109
|
+
lines.push(formatStep(step, i));
|
|
110
|
+
});
|
|
111
|
+
lines.push("");
|
|
112
|
+
if (def.methodology) {
|
|
113
|
+
lines.push("## Methodology");
|
|
114
|
+
lines.push("");
|
|
115
|
+
lines.push(def.methodology);
|
|
116
|
+
lines.push("");
|
|
117
|
+
}
|
|
118
|
+
return lines.join("\n");
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
// src/agent-definitions/render-gemini-cli.ts
|
|
122
|
+
function toGeminiToolName(tool) {
|
|
123
|
+
return GEMINI_TOOL_MAP[tool] ?? tool;
|
|
124
|
+
}
|
|
125
|
+
function formatStep2(step, index) {
|
|
126
|
+
if ("command" in step && step.command) {
|
|
127
|
+
const cmd = step.command;
|
|
128
|
+
const when = step.when ?? "always";
|
|
129
|
+
return `${index + 1}. Run \`harness ${cmd}\` (${when})`;
|
|
130
|
+
}
|
|
131
|
+
if ("skill" in step && step.skill) {
|
|
132
|
+
const skill = step.skill;
|
|
133
|
+
const when = step.when ?? "always";
|
|
134
|
+
return `${index + 1}. Execute ${skill} skill (${when})`;
|
|
135
|
+
}
|
|
136
|
+
return `${index + 1}. Unknown step`;
|
|
137
|
+
}
|
|
138
|
+
function renderGeminiAgent(def) {
|
|
139
|
+
const lines = ["---"];
|
|
140
|
+
lines.push(`name: ${def.name}`);
|
|
141
|
+
lines.push(`description: >`);
|
|
142
|
+
lines.push(` ${def.description}`);
|
|
143
|
+
if (def.tools.length > 0) {
|
|
144
|
+
lines.push("tools:");
|
|
145
|
+
for (const tool of def.tools) {
|
|
146
|
+
lines.push(` - ${toGeminiToolName(tool)}`);
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
lines.push("---");
|
|
150
|
+
lines.push("");
|
|
151
|
+
lines.push(GENERATED_HEADER_AGENT);
|
|
152
|
+
lines.push("");
|
|
153
|
+
lines.push("## Role");
|
|
154
|
+
lines.push("");
|
|
155
|
+
lines.push(def.role);
|
|
156
|
+
lines.push("");
|
|
157
|
+
lines.push("## Skills");
|
|
158
|
+
lines.push("");
|
|
159
|
+
for (const skill of def.skills) {
|
|
160
|
+
lines.push(`- ${skill}`);
|
|
161
|
+
}
|
|
162
|
+
lines.push("");
|
|
163
|
+
lines.push("## Steps");
|
|
164
|
+
lines.push("");
|
|
165
|
+
def.steps.forEach((step, i) => {
|
|
166
|
+
lines.push(formatStep2(step, i));
|
|
167
|
+
});
|
|
168
|
+
lines.push("");
|
|
169
|
+
if (def.methodology) {
|
|
170
|
+
lines.push("## Methodology");
|
|
171
|
+
lines.push("");
|
|
172
|
+
lines.push(def.methodology);
|
|
173
|
+
lines.push("");
|
|
174
|
+
}
|
|
175
|
+
return lines.join("\n");
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
// src/commands/generate-agent-definitions.ts
|
|
179
|
+
function resolveOutputDir(platform, opts) {
|
|
180
|
+
if (opts.output) {
|
|
181
|
+
return platform === "claude-code" ? path.join(opts.output, "claude-code") : path.join(opts.output, "gemini-cli");
|
|
182
|
+
}
|
|
183
|
+
if (opts.global) {
|
|
184
|
+
const home = os.homedir();
|
|
185
|
+
return platform === "claude-code" ? path.join(home, ".claude", "agents") : path.join(home, ".gemini", "agents");
|
|
186
|
+
}
|
|
187
|
+
return platform === "claude-code" ? path.join("agents", "agents", "claude-code") : path.join("agents", "agents", "gemini-cli");
|
|
188
|
+
}
|
|
189
|
+
function loadSkillContent(skillName) {
|
|
190
|
+
const skillsDir = resolveSkillsDir();
|
|
191
|
+
const skillMdPath = path.join(skillsDir, skillName, "SKILL.md");
|
|
192
|
+
if (!fs.existsSync(skillMdPath)) return null;
|
|
193
|
+
return fs.readFileSync(skillMdPath, "utf-8");
|
|
194
|
+
}
|
|
195
|
+
function getRenderer(platform) {
|
|
196
|
+
return platform === "claude-code" ? renderClaudeCodeAgent : renderGeminiAgent;
|
|
197
|
+
}
|
|
198
|
+
function generateAgentDefinitions(opts) {
|
|
199
|
+
const personasDir = resolvePersonasDir();
|
|
200
|
+
const personaList = listPersonas(personasDir);
|
|
201
|
+
if (!personaList.ok) return [];
|
|
202
|
+
const personas = personaList.value.map((meta) => loadPersona(meta.filePath)).filter((r) => r.ok).map((r) => r.value);
|
|
203
|
+
const allSkillNames = new Set(personas.flatMap((p) => p.skills));
|
|
204
|
+
const skillContents = /* @__PURE__ */ new Map();
|
|
205
|
+
for (const skillName of allSkillNames) {
|
|
206
|
+
const content = loadSkillContent(skillName);
|
|
207
|
+
if (content) {
|
|
208
|
+
skillContents.set(skillName, content);
|
|
209
|
+
}
|
|
210
|
+
}
|
|
211
|
+
const definitions = personas.map((p) => generateAgentDefinition(p, skillContents));
|
|
212
|
+
const results = [];
|
|
213
|
+
for (const platform of opts.platforms) {
|
|
214
|
+
const outputDir = resolveOutputDir(platform, opts);
|
|
215
|
+
const renderer = getRenderer(platform);
|
|
216
|
+
const rendered = /* @__PURE__ */ new Map();
|
|
217
|
+
for (const def of definitions) {
|
|
218
|
+
const filename = `${def.name}.md`;
|
|
219
|
+
rendered.set(filename, renderer(def));
|
|
220
|
+
}
|
|
221
|
+
const plan = computeSyncPlan(outputDir, rendered);
|
|
222
|
+
if (!opts.dryRun) {
|
|
223
|
+
applySyncPlan(outputDir, rendered, plan, false);
|
|
224
|
+
}
|
|
225
|
+
results.push({
|
|
226
|
+
platform,
|
|
227
|
+
added: plan.added,
|
|
228
|
+
updated: plan.updated,
|
|
229
|
+
removed: plan.removed,
|
|
230
|
+
unchanged: plan.unchanged,
|
|
231
|
+
outputDir
|
|
232
|
+
});
|
|
233
|
+
}
|
|
234
|
+
return results;
|
|
235
|
+
}
|
|
236
|
+
function createGenerateAgentDefinitionsCommand() {
|
|
237
|
+
return new Command("generate-agent-definitions").description("Generate agent definition files from personas for Claude Code and Gemini CLI").option("--platforms <list>", "Target platforms (comma-separated)", "claude-code,gemini-cli").option("--global", "Write to global agent directories", false).option("--output <dir>", "Custom output directory").option("--dry-run", "Show what would change without writing", false).action(async (opts, cmd) => {
|
|
238
|
+
const globalOpts = cmd.optsWithGlobals();
|
|
239
|
+
const platforms = opts.platforms.split(",").map((p) => p.trim());
|
|
240
|
+
for (const p of platforms) {
|
|
241
|
+
if (!VALID_PLATFORMS.includes(p)) {
|
|
242
|
+
throw new CLIError(
|
|
243
|
+
`Invalid platform "${p}". Valid platforms: ${VALID_PLATFORMS.join(", ")}`,
|
|
244
|
+
ExitCode.VALIDATION_FAILED
|
|
245
|
+
);
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
try {
|
|
249
|
+
const results = generateAgentDefinitions({
|
|
250
|
+
platforms,
|
|
251
|
+
global: opts.global,
|
|
252
|
+
output: opts.output,
|
|
253
|
+
dryRun: opts.dryRun
|
|
254
|
+
});
|
|
255
|
+
if (globalOpts.json) {
|
|
256
|
+
console.log(JSON.stringify(results, null, 2));
|
|
257
|
+
return;
|
|
258
|
+
}
|
|
259
|
+
for (const result of results) {
|
|
260
|
+
console.log(`
|
|
261
|
+
${result.platform} \u2192 ${result.outputDir}`);
|
|
262
|
+
if (result.added.length > 0) {
|
|
263
|
+
console.log(` + ${result.added.length} new: ${result.added.join(", ")}`);
|
|
264
|
+
}
|
|
265
|
+
if (result.updated.length > 0) {
|
|
266
|
+
console.log(` ~ ${result.updated.length} updated: ${result.updated.join(", ")}`);
|
|
267
|
+
}
|
|
268
|
+
if (result.removed.length > 0) {
|
|
269
|
+
console.log(` - ${result.removed.length} removed: ${result.removed.join(", ")}`);
|
|
270
|
+
}
|
|
271
|
+
if (result.unchanged.length > 0) {
|
|
272
|
+
console.log(` = ${result.unchanged.length} unchanged`);
|
|
273
|
+
}
|
|
274
|
+
if (opts.dryRun) {
|
|
275
|
+
console.log(" (dry run \u2014 no files written)");
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
} catch (error) {
|
|
279
|
+
handleError(error);
|
|
280
|
+
}
|
|
281
|
+
});
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
export {
|
|
285
|
+
AGENT_DESCRIPTIONS,
|
|
286
|
+
DEFAULT_TOOLS,
|
|
287
|
+
GEMINI_TOOL_MAP,
|
|
288
|
+
generateAgentDefinition,
|
|
289
|
+
renderClaudeCodeAgent,
|
|
290
|
+
renderGeminiAgent,
|
|
291
|
+
generateAgentDefinitions,
|
|
292
|
+
createGenerateAgentDefinitionsCommand
|
|
293
|
+
};
|