@walwal-harness/cli 7.1.40 → 7.1.42

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 (84) hide show
  1. package/HR-Resource/cdo/SKILL.md +9 -1
  2. package/HR-Resource/ceo/SKILL.md +33 -2
  3. package/HR-Resource/coo/SKILL.md +9 -1
  4. package/HR-Resource/cqo/SKILL.md +9 -1
  5. package/HR-Resource/cto/SKILL.md +10 -2
  6. package/HR-Resource/ops/SKILL.md +12 -4
  7. package/HR-Resource/ops-prompt-inspector/SKILL.md +11 -6
  8. package/HR-Resource/ops-prompt-inspector/assets/prompt-inspector-static.js +180 -0
  9. package/HR-Resource/ops-prompt-inspector/scripts/setup.py +66 -3
  10. package/apps/harness-dashboard/app/api/metrics/route.ts +17 -0
  11. package/apps/harness-dashboard/app/api/wake/route.ts +41 -0
  12. package/apps/harness-dashboard/app/brick.css +482 -0
  13. package/apps/harness-dashboard/app/layout.tsx +13 -0
  14. package/apps/harness-dashboard/app/page.tsx +2 -2
  15. package/apps/harness-dashboard/components/Scene.tsx +690 -36
  16. package/apps/harness-dashboard/components/brick/BrickDashboard.tsx +149 -0
  17. package/apps/harness-dashboard/components/brick/reports.tsx +291 -0
  18. package/apps/harness-dashboard/components/brick/tweaks.tsx +738 -0
  19. package/apps/harness-dashboard/components/brick/ui.tsx +463 -0
  20. package/apps/harness-dashboard/components/brick/views-graph.tsx +305 -0
  21. package/apps/harness-dashboard/components/brick/views-grid.tsx +543 -0
  22. package/apps/harness-dashboard/components/brick/views-timeline.tsx +238 -0
  23. package/apps/harness-dashboard/lib/__tests__/harness-state.test.ts +1 -202
  24. package/apps/harness-dashboard/lib/__tests__/sandbox-e2e.test.ts +490 -0
  25. package/apps/harness-dashboard/lib/brick/adapter.ts +423 -0
  26. package/apps/harness-dashboard/lib/brick/contract.ts +247 -0
  27. package/apps/harness-dashboard/lib/harness-state.ts +107 -796
  28. package/apps/harness-dashboard/lib/metrics/sampler.ts +545 -0
  29. package/apps/harness-dashboard/lib/types.ts +22 -222
  30. package/apps/harness-dashboard/playwright.config.ts +26 -7
  31. package/assets/templates/AGENTS-ko.md.template +1 -1
  32. package/assets/templates/AGENTS.md.template +12 -2
  33. package/assets/templates/HARNESS.md +2 -0
  34. package/assets/templates/company-pipeline-manifest.json +5 -14
  35. package/assets/templates/worker-report.md.template +38 -0
  36. package/bin/init.js +2 -1
  37. package/commands/goal.md +4 -2
  38. package/commands/hot-fix.md +1 -1
  39. package/commands/submission.md +1 -1
  40. package/package.json +1 -1
  41. package/scripts/conductor-tick.sh +12 -0
  42. package/scripts/harness-agenda.sh +105 -0
  43. package/scripts/harness-company-block.sh +89 -0
  44. package/scripts/harness-company-complete.sh +17 -8
  45. package/scripts/harness-company-cycle.sh +54 -0
  46. package/scripts/harness-progress-set.sh +8 -2
  47. package/scripts/harness-stop.sh +76 -0
  48. package/scripts/harness-wake-control.sh +151 -0
  49. package/scripts/harness-wake.sh +5 -0
  50. package/scripts/harness-worker-dispatch.sh +31 -7
  51. package/apps/harness-dashboard/components/Drawer.tsx +0 -146
  52. package/apps/harness-dashboard/components/Header.tsx +0 -40
  53. package/apps/harness-dashboard/components/MissionTimeline.tsx +0 -214
  54. package/apps/harness-dashboard/components/OrgTree.tsx +0 -459
  55. package/apps/harness-dashboard/components/drawer/AgentLogTab.tsx +0 -56
  56. package/apps/harness-dashboard/components/drawer/DesignPreviewTab.tsx +0 -160
  57. package/apps/harness-dashboard/components/drawer/GotchasTab.tsx +0 -89
  58. package/apps/harness-dashboard/components/drawer/HypothesisTab.tsx +0 -42
  59. package/apps/harness-dashboard/components/drawer/IncidentsTab.tsx +0 -50
  60. package/apps/harness-dashboard/components/drawer/MissionDocTab.tsx +0 -96
  61. package/apps/harness-dashboard/components/drawer/MissionFlowTab.tsx +0 -576
  62. package/apps/harness-dashboard/components/drawer/OwnerHistoryTab.tsx +0 -160
  63. package/apps/harness-dashboard/components/drawer/RoomMetricsTab.tsx +0 -90
  64. package/apps/harness-dashboard/components/drawer/TracksTab.tsx +0 -47
  65. package/apps/harness-dashboard/components/three/ArchiveBoxes.tsx +0 -95
  66. package/apps/harness-dashboard/components/three/DeptBoard.tsx +0 -175
  67. package/apps/harness-dashboard/components/three/Floor3D.tsx +0 -404
  68. package/apps/harness-dashboard/components/three/GoalCard3D.tsx +0 -123
  69. package/apps/harness-dashboard/components/three/HypothesisCards.tsx +0 -71
  70. package/apps/harness-dashboard/components/three/MeetingWhiteboard.tsx +0 -98
  71. package/apps/harness-dashboard/components/three/Minifig3D.tsx +0 -391
  72. package/apps/harness-dashboard/components/three/OpsSiren.tsx +0 -99
  73. package/apps/harness-dashboard/components/three/Stage3D.tsx +0 -104
  74. package/apps/harness-dashboard/components/three/TrackRibbons.tsx +0 -81
  75. package/apps/harness-dashboard/lib/__tests__/i18n.test.ts +0 -16
  76. package/apps/harness-dashboard/lib/__tests__/iso.test.ts +0 -42
  77. package/apps/harness-dashboard/lib/__tests__/state-mapping.test.ts +0 -183
  78. package/apps/harness-dashboard/lib/agent-roster.ts +0 -42
  79. package/apps/harness-dashboard/lib/furniture.ts +0 -165
  80. package/apps/harness-dashboard/lib/i18n.ts +0 -26
  81. package/apps/harness-dashboard/lib/iso.ts +0 -150
  82. package/apps/harness-dashboard/lib/markdown.tsx +0 -306
  83. package/apps/harness-dashboard/lib/path-planning.ts +0 -72
  84. package/apps/harness-dashboard/lib/state-mapping.ts +0 -146
@@ -0,0 +1,238 @@
1
+ "use client";
2
+
3
+ /* =============================================================
4
+ walwal-harness · VIEW 3 — TIMELINE (cadence heatmap + swimlanes)
5
+ Ported from harness/views-timeline.jsx (design handoff).
6
+ Exports: TimelineView, Cadence
7
+ ============================================================= */
8
+
9
+ import React, { useRef } from "react";
10
+ import type { CSSProperties } from "react";
11
+
12
+ import type {
13
+ AgentRole,
14
+ ContractState,
15
+ ContractWorker,
16
+ DocTarget,
17
+ } from "../../lib/brick/contract";
18
+ import { StatusDot, Label } from "./ui";
19
+
20
+ const SPAN_MS = 12 * 3600 * 1000; // 12h window, now=left
21
+
22
+ /** Inline style that also carries the per-agent `--hue` CSS custom property. */
23
+ type HueStyle = CSSProperties & { "--hue": string };
24
+
25
+ /* ---- Cadence (also rendered by the COMMAND view) ---------------------- */
26
+
27
+ export interface CadenceProps {
28
+ /** 24 hourly buckets = owner prompts/hour. */
29
+ cadence: number[];
30
+ }
31
+
32
+ export function Cadence({ cadence }: CadenceProps) {
33
+ const max = Math.max(...cadence, 1);
34
+ return (
35
+ <div className="cadence">
36
+ <Label right={"max " + max + " · 24h"}>CADENCE · owner prompts / h</Label>
37
+ <div className="cad-row">
38
+ {cadence.map((v, i) => (
39
+ <div
40
+ key={i}
41
+ className="cad-cell"
42
+ title={v + " / h"}
43
+ style={{
44
+ background:
45
+ v === 0 ? "transparent" : `rgba(229,72,77,${0.28 + 0.55 * (v / max)})`,
46
+ borderColor: v === 0 ? "var(--bd)" : "rgba(229,72,77,0.5)",
47
+ }}
48
+ />
49
+ ))}
50
+ </div>
51
+ <div className="cad-axis">
52
+ <span>now</span>
53
+ <span>−12h</span>
54
+ <span>−24h</span>
55
+ </div>
56
+ </div>
57
+ );
58
+ }
59
+
60
+ /* ---- TimelineView ----------------------------------------------------- */
61
+
62
+ export interface TimelineViewProps {
63
+ /** The single source-of-truth contract state. */
64
+ s: ContractState;
65
+ /** Open a document (agent report or worker brief) in the DocViewer. */
66
+ openDoc?: (target: DocTarget) => void;
67
+ }
68
+
69
+ type SwimMark = { ago: number; dur: number };
70
+
71
+ type SwimRow = {
72
+ kind: "exec" | "worker";
73
+ id: string;
74
+ label: string;
75
+ hue: string;
76
+ agent: AgentRole;
77
+ status: string;
78
+ progress?: number | null;
79
+ };
80
+
81
+ export function TimelineView({ s, openDoc }: TimelineViewProps) {
82
+ // stable seeded marks per row id
83
+ const markCache = useRef<Record<string, SwimMark[]>>({});
84
+ function seedMarks(id: string, density: number): SwimMark[] {
85
+ const cached = markCache.current[id];
86
+ if (cached) return cached;
87
+ const arr: SwimMark[] = [];
88
+ const n = Math.floor(density * (4 + Math.random() * 7));
89
+ for (let i = 0; i < n; i++) {
90
+ arr.push({ ago: Math.random() * SPAN_MS, dur: 40000 + Math.random() * 600000 });
91
+ }
92
+ markCache.current[id] = arr;
93
+ return arr;
94
+ }
95
+
96
+ // build rows: exec + its workers
97
+ const order: AgentRole[] = ["ceo", "coo", "cto", "cqo", "cdo", "ops"];
98
+ const rows: SwimRow[] = [];
99
+ order.forEach((id) => {
100
+ const a = s.agents.find((x) => x.id === id);
101
+ if (!a) return;
102
+ rows.push({ kind: "exec", id: a.id, label: a.name, hue: a.hue, agent: a.id, status: a.status });
103
+ s.workers
104
+ .filter((w) => w.agent === id)
105
+ .forEach((w) => {
106
+ rows.push({
107
+ kind: "worker",
108
+ id: w.id,
109
+ label: w.name,
110
+ hue: a.hue,
111
+ agent: a.id,
112
+ status: w.status,
113
+ progress: w.progress,
114
+ });
115
+ });
116
+ });
117
+
118
+ // live marks from recent events (last 6 min) keyed to exec rows
119
+ const liveByAgent: Record<string, number[]> = {};
120
+ s.events.forEach((e) => {
121
+ if (e.at == null || e.agent === "") return;
122
+ const age = s.now - e.at;
123
+ if (age < 6 * 60 * 1000) {
124
+ (liveByAgent[e.agent] = liveByAgent[e.agent] || []).push(age);
125
+ }
126
+ });
127
+
128
+ const xOf = (ago: number): number => Math.max(0, Math.min(100, (ago / SPAN_MS) * 100));
129
+
130
+ // axis ticks
131
+ const ticks: number[] = [];
132
+ for (let h = 0; h <= 12; h += 2) ticks.push(h);
133
+
134
+ const openRow = (r: SwimRow) => {
135
+ if (!openDoc) return;
136
+ if (r.kind === "exec") {
137
+ openDoc({ type: "agent", agent: r.agent });
138
+ return;
139
+ }
140
+ const worker: ContractWorker | undefined = s.workers.find((w) => w.id === r.id);
141
+ if (worker) openDoc({ type: "worker", agent: r.agent, worker });
142
+ };
143
+
144
+ return (
145
+ <div className="timelineview">
146
+ <Cadence cadence={s.cadence} />
147
+ <div className="swim">
148
+ <Label
149
+ right={
150
+ rows.filter((r) => r.kind === "worker").length +
151
+ " workers · " +
152
+ order.length +
153
+ " execs"
154
+ }
155
+ >
156
+ ORCHESTRATION TIMELINE · now → −12h
157
+ </Label>
158
+ <div className="swim-axis">
159
+ <div className="swim-axis-pad" />
160
+ <div className="swim-axis-track">
161
+ {ticks.map((h) => (
162
+ <span
163
+ key={h}
164
+ className="swim-tick"
165
+ style={{ left: (h / 12) * 100 + "%" }}
166
+ >
167
+ {h === 0 ? "now" : "−" + h + "h"}
168
+ </span>
169
+ ))}
170
+ </div>
171
+ </div>
172
+ <div className="swim-rows">
173
+ {rows.map((r) => {
174
+ const marks = seedMarks(r.id, r.kind === "exec" ? 1.4 : 0.8);
175
+ const live = r.kind === "exec" ? liveByAgent[r.agent] || [] : [];
176
+ return (
177
+ <div
178
+ key={r.id}
179
+ className={"swim-row " + (r.kind === "exec" ? "is-exec" : "is-worker")}
180
+ onClick={() => openRow(r)}
181
+ >
182
+ <div className="swim-label" style={{ "--hue": r.hue } as HueStyle}>
183
+ {r.kind === "exec" ? (
184
+ <span
185
+ className="glyph glyph-sm"
186
+ style={{ color: r.hue, borderColor: r.hue + "55" }}
187
+ >
188
+ {r.label}
189
+ </span>
190
+ ) : (
191
+ <span className="swim-wlabel">
192
+ <span className="swim-tree">└</span>
193
+ {r.label}
194
+ </span>
195
+ )}
196
+ {r.kind === "exec" && <StatusDot status={r.status} size={6} />}
197
+ </div>
198
+ <div className="swim-track">
199
+ <div className="swim-gridlines">
200
+ {ticks.map((h) => (
201
+ <span key={h} style={{ left: (h / 12) * 100 + "%" }} />
202
+ ))}
203
+ </div>
204
+ {marks.map((m, i) => (
205
+ <span
206
+ key={i}
207
+ className="swim-block"
208
+ style={{
209
+ left: xOf(m.ago) + "%",
210
+ width: Math.max(0.6, (m.dur / SPAN_MS) * 100) + "%",
211
+ background: r.hue,
212
+ opacity: r.kind === "exec" ? 0.85 : 0.55,
213
+ }}
214
+ />
215
+ ))}
216
+ {live.map((age, i) => (
217
+ <span
218
+ key={"l" + i}
219
+ className="swim-live"
220
+ style={{ left: xOf(age) + "%", background: r.hue }}
221
+ />
222
+ ))}
223
+ {r.kind === "worker" && r.progress != null && (
224
+ <span
225
+ className="swim-now-prog"
226
+ style={{ background: r.hue }}
227
+ title={Math.round(r.progress) + "%"}
228
+ />
229
+ )}
230
+ </div>
231
+ </div>
232
+ );
233
+ })}
234
+ </div>
235
+ </div>
236
+ </div>
237
+ );
238
+ }
@@ -3,7 +3,6 @@ import { mkdtempSync, mkdirSync, rmSync, utimesSync, writeFileSync } from "node:
3
3
  import { tmpdir } from "node:os";
4
4
  import path from "node:path";
5
5
  import { readHarnessState } from "../harness-state";
6
- import { AGENT_ROSTER } from "../agent-roster";
7
6
 
8
7
  describe("readHarnessState", () => {
9
8
  let dir: string;
@@ -16,54 +15,9 @@ describe("readHarnessState", () => {
16
15
  rmSync(dir, { recursive: true, force: true });
17
16
  });
18
17
 
19
- it("valid progress.json: derives typing for current_agent, talking for meetings.active, idle for the rest", () => {
20
- mkdirSync(path.join(dir, ".harness"), { recursive: true });
21
- writeFileSync(
22
- path.join(dir, ".harness", "progress.json"),
23
- JSON.stringify({
24
- sprint: { number: 1 },
25
- current_agent: "generator-backend",
26
- agent_status: "running",
27
- meetings: { active: ["planner"], cadence: "normal", next_scheduled: null },
28
- cto: { last_review: "2026-05-07", open_arch_risks: 0 },
29
- cqo: { last_audit: null, sprint_verdict: "pending", open_regressions: 0 },
30
- service_ops: { monitor: { last_check: "2026-05-07", alerts_this_sprint: 0 } },
31
- goals: {
32
- active_id: "g1",
33
- list: [{ id: "g1", title: "Brick Office MVP", description: "Phase C launch" }],
34
- current_adherence: 0.6,
35
- },
36
- })
37
- );
38
-
39
- const snap = readHarnessState(dir);
40
- expect(snap.errorBanner).toBeNull();
41
- expect(snap.agents.length).toBe(AGENT_ROSTER.length);
42
- expect(snap.agents.map((a) => a.id).sort()).toEqual(
43
- AGENT_ROSTER.map((a) => a.id).sort()
44
- );
45
- const stateOf = (id: string) => snap.agents.find((a) => a.id === id)!.minifigState;
46
- expect(stateOf("generator-backend")).toBe("typing");
47
- expect(stateOf("planner")).toBe("talking");
48
- expect(stateOf("dispatcher")).toBe("idle");
49
- expect(snap.rooms.length).toBe(7);
50
-
51
- const planner = snap.agents.find((a) => a.id === "planner")!;
52
- expect(planner.room).toBe("meeting");
53
- expect(planner.homeRoom).toBe("coo");
54
-
55
- const meetingRoom = snap.rooms.find((r) => r.id === "meeting")!;
56
- expect(meetingRoom.seatLayout).toBeDefined();
57
- expect(meetingRoom.seatLayout!.occupants).toContain("planner");
58
-
59
- expect(snap.goal).not.toBeNull();
60
- expect(snap.goal!.title).toBe("Brick Office MVP");
61
- });
62
-
63
18
  it("missing .harness: returns error banner, no crash", () => {
64
19
  const snap = readHarnessState(dir);
65
20
  expect(snap.errorBanner?.level).toBe("error");
66
- expect(snap.agents.length).toBe(AGENT_ROSTER.length);
67
21
  });
68
22
 
69
23
  it("corrupt progress.json: returns error banner, no crash", () => {
@@ -72,124 +26,6 @@ describe("readHarnessState", () => {
72
26
  const snap = readHarnessState(dir);
73
27
  expect(snap.errorBanner?.level).toBe("error");
74
28
  expect(snap.errorBanner?.message_en).toContain("corrupt");
75
- expect(snap.agents.length).toBe(AGENT_ROSTER.length);
76
- });
77
-
78
- it("v6 NEXUS: roster includes CTO, CQO, Brainstormer", () => {
79
- const ids = AGENT_ROSTER.map((a) => a.id);
80
- expect(ids).toContain("cto");
81
- expect(ids).toContain("cqo");
82
- expect(ids).toContain("brainstormer");
83
- });
84
-
85
- it("parallel tracks, hypothesis, escalations, incidents land in the snapshot", () => {
86
- mkdirSync(path.join(dir, ".harness"), { recursive: true });
87
- writeFileSync(
88
- path.join(dir, ".harness", "progress.json"),
89
- JSON.stringify({
90
- sprint: { number: 3 },
91
- pipeline: "FULLSTACK",
92
- current_agent: "conductor",
93
- agent_status: "running",
94
- meetings: {
95
- active: [],
96
- cadence: "heavy",
97
- next_scheduled: "2026-05-08T10:00Z",
98
- current: { type: "incident-war-room", topic: "P0 prod outage" },
99
- },
100
- cto: {
101
- last_review: "2026-05-07",
102
- open_arch_risks: 1,
103
- contract_signed: { be: true, fe: false },
104
- },
105
- cqo: {
106
- last_audit: "2026-05-07",
107
- sprint_verdict: "pending",
108
- open_regressions: 2,
109
- last_scores: {
110
- functional: 2.9,
111
- visual: 2.8,
112
- code_quality: 2.5,
113
- architecture: 2.95,
114
- security: 3.0,
115
- },
116
- },
117
- service_ops: {
118
- monitor: { last_check: "2026-05-07", alerts_this_sprint: 4 },
119
- incident: {
120
- open: [
121
- { id: "INC-1", dept: "CTO", severity: "critical", message: "DB down" },
122
- { id: "INC-2", dept: "Operations", severity: "medium" },
123
- ],
124
- },
125
- },
126
- parallel_tracks: [
127
- {
128
- id: "T-1",
129
- from_meeting: "spec-review",
130
- to_dept: "CTO",
131
- to_room: "cto-team",
132
- status: "in_progress",
133
- },
134
- {
135
- id: "T-2",
136
- from_meeting: "spec-review",
137
- to_dept: "Planner",
138
- to_room: "coo",
139
- status: "dispatched",
140
- },
141
- ],
142
- hypothesis: {
143
- active: [
144
- { id: "H-1", brief: "Cache hit > 80%", verdict: "pending" },
145
- { id: "H-2", brief: "p95 < 200ms", verdict: "valid" },
146
- ],
147
- },
148
- escalations: {
149
- open: [{ id: "E-1", reason: "three-fail", message: "regression x3" }],
150
- },
151
- contracts: {
152
- api: { version: "v2.1.0" },
153
- feature_list: { total: 16, passed: 12, failed: 1 },
154
- },
155
- })
156
- );
157
-
158
- const snap = readHarnessState(dir);
159
- expect(snap.errorBanner).toBeNull();
160
-
161
- expect(snap.tracks.map((t) => t.id)).toEqual(["T-1", "T-2"]);
162
- expect(snap.incidents.length).toBe(2);
163
- expect(snap.hypothesis.length).toBe(2);
164
- expect(snap.escalations.length).toBe(1);
165
- expect(snap.contract.pipeline).toBe("FULLSTACK");
166
- expect(snap.contract.sprint_number).toBe(3);
167
- expect(snap.contract.feature_total).toBe(16);
168
- expect(snap.contract.contract_signed).toEqual({ be: true, fe: false });
169
- expect(snap.evalScores?.code_quality).toBe(2.5);
170
- expect(snap.meetings.cadence).toBe("heavy");
171
- expect(snap.meetings.current?.type).toBe("incident-war-room");
172
-
173
- // CTO has an open incident → CTO-dept agents go red-alert; Service-Ops
174
- // is on-call and is *always* red when any incident is open.
175
- const stateOf = (id: string) => snap.agents.find((a) => a.id === id)!.minifigState;
176
- expect(stateOf("cto")).toBe("red-alert");
177
- expect(stateOf("service-ops")).toBe("red-alert");
178
- expect(stateOf("evaluator-visual")).toBe("idle"); // CQO dept untouched
179
- });
180
-
181
- it("buildArchive reads verdict.json when present", () => {
182
- const sprintDir = path.join(dir, ".harness", "archive", "sprint-1");
183
- mkdirSync(sprintDir, { recursive: true });
184
- writeFileSync(path.join(sprintDir, "verdict.json"), JSON.stringify({ result: "PASS" }));
185
- mkdirSync(path.join(dir, ".harness"), { recursive: true });
186
- writeFileSync(
187
- path.join(dir, ".harness", "progress.json"),
188
- JSON.stringify({ sprint: { number: 1 } })
189
- );
190
-
191
- const snap = readHarnessState(dir);
192
- expect(snap.archive.all.find((e) => e.dir === "sprint-1")?.result).toBe("PASS");
193
29
  });
194
30
 
195
31
  it("marks in-place goal document updates as submission only after the owner prompt", () => {
@@ -403,44 +239,11 @@ describe("readHarnessState", () => {
403
239
  const workers = readHarnessState(dir).missions[0].workers;
404
240
  expect(workers[0]).toMatchObject({
405
241
  name: "frontend-worker",
406
- status: "COMPLETE",
242
+ status: "unknown",
407
243
  active: false,
408
244
  });
409
245
  });
410
246
 
411
- it("reads manual worker telemetry with name, progress, eta, and report_path", () => {
412
- const harnessDir = path.join(dir, ".harness");
413
- mkdirSync(harnessDir, { recursive: true });
414
- writeFileSync(
415
- path.join(harnessDir, "progress.json"),
416
- JSON.stringify({
417
- agent_status: "running",
418
- company_state: {
419
- active_workers: 2,
420
- workers: [
421
- {
422
- name: "frontend-engineer-multi-strategy",
423
- status: "running",
424
- progress: "70%",
425
- eta: "2026-05-31 17:00",
426
- report_path: ".harness/documents/goal-1/cto/workers/frontend-engineer-multi-strategy.md",
427
- },
428
- ],
429
- },
430
- })
431
- );
432
-
433
- const worker = readHarnessState(dir).dashboard.workers[0];
434
- expect(worker).toMatchObject({
435
- agent: "frontend-engineer-multi-strategy",
436
- feature: "frontend-engineer-multi-strategy",
437
- status: "running",
438
- log: ".harness/documents/goal-1/cto/workers/frontend-engineer-multi-strategy.md",
439
- progress: 0.7,
440
- });
441
- expect(worker.summary).toContain("2026-05-31 17:00");
442
- });
443
-
444
247
  it("accepts keyed company_state.workers maps from manual CXX telemetry", () => {
445
248
  const harnessDir = path.join(dir, ".harness");
446
249
  const missionDir = path.join(harnessDir, "documents", "goal-1-dashboard");
@@ -468,10 +271,6 @@ describe("readHarnessState", () => {
468
271
  );
469
272
 
470
273
  const snap = readHarnessState(dir);
471
- expect(snap.dashboard.workers[0]).toMatchObject({
472
- agent: "engineering-engineering-code-reviewer",
473
- status: "running",
474
- });
475
274
  expect(snap.missions[0].workers[0]).toMatchObject({
476
275
  owner: "cqo",
477
276
  active: true,