@harness-engineering/cli 1.25.7 → 1.26.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 (61) hide show
  1. package/dist/agents/skills/claude-code/harness-knowledge-pipeline/SKILL.md +277 -0
  2. package/dist/agents/skills/claude-code/harness-knowledge-pipeline/skill.yaml +60 -0
  3. package/dist/agents/skills/codex/harness-knowledge-pipeline/SKILL.md +277 -0
  4. package/dist/agents/skills/codex/harness-knowledge-pipeline/skill.yaml +60 -0
  5. package/dist/agents/skills/cursor/harness-knowledge-pipeline/SKILL.md +277 -0
  6. package/dist/agents/skills/cursor/harness-knowledge-pipeline/skill.yaml +60 -0
  7. package/dist/agents/skills/gemini-cli/harness-knowledge-pipeline/SKILL.md +277 -0
  8. package/dist/agents/skills/gemini-cli/harness-knowledge-pipeline/skill.yaml +60 -0
  9. package/dist/agents/skills/package.json +2 -2
  10. package/dist/{agents-md-QPO3H5HX.js → agents-md-OPOZA5L7.js} +3 -3
  11. package/dist/{architecture-IJLXRHZA.js → architecture-PMVMO6SF.js} +4 -4
  12. package/dist/{assess-project-QU6XIVJK.js → assess-project-ZW7EKNIT.js} +1 -1
  13. package/dist/bin/harness-mcp.js +15 -15
  14. package/dist/bin/harness.js +25 -25
  15. package/dist/{check-phase-gate-TNY64AOS.js → check-phase-gate-NTLAU3LO.js} +4 -4
  16. package/dist/{chunk-TQRCODRJ.js → chunk-4KSKV5MK.js} +1 -1
  17. package/dist/{chunk-IT2KORSK.js → chunk-6SCA4NEZ.js} +1 -1
  18. package/dist/{chunk-ZIYLIYN4.js → chunk-77EZGPSR.js} +1 -1
  19. package/dist/{chunk-D3XL2FLX.js → chunk-7JNZXJKY.js} +5 -5
  20. package/dist/{chunk-JJQ3TW2E.js → chunk-CAS3TS4Y.js} +101 -89
  21. package/dist/{chunk-K35D7HF3.js → chunk-EXTWTJRF.js} +1 -1
  22. package/dist/{chunk-AS5DQT4S.js → chunk-FI3D6D7U.js} +9 -9
  23. package/dist/{chunk-2DF6OZLG.js → chunk-G6SYTGOH.js} +2 -2
  24. package/dist/{chunk-KVJZQ2MV.js → chunk-HAOBHL3W.js} +1 -1
  25. package/dist/{chunk-MLOGYWLY.js → chunk-IFHAUFJX.js} +2 -2
  26. package/dist/{chunk-IQO7IINR.js → chunk-J3O64D2A.js} +1 -1
  27. package/dist/{chunk-LTCEV7VF.js → chunk-JBJ4AVE4.js} +3 -3
  28. package/dist/{chunk-FRDS4XGD.js → chunk-JWSVLC4I.js} +1 -1
  29. package/dist/{chunk-K533WNZG.js → chunk-JZ6GORAK.js} +1 -1
  30. package/dist/{chunk-YRBNAHH4.js → chunk-KFE2X7LG.js} +4 -4
  31. package/dist/{chunk-MCDCZMKN.js → chunk-KSFUJT5B.js} +1 -1
  32. package/dist/{chunk-LXPRO2FH.js → chunk-KXIAHHHP.js} +2 -2
  33. package/dist/{chunk-E5Z6NTTQ.js → chunk-NIOB6FTG.js} +1 -1
  34. package/dist/{chunk-PCOU2UXU.js → chunk-NVGQO4VM.js} +8 -8
  35. package/dist/{chunk-G5SNXUIK.js → chunk-QYSWNPXZ.js} +1 -1
  36. package/dist/{chunk-XVJRFP7W.js → chunk-RNAGPTKF.js} +6 -6
  37. package/dist/{chunk-GVNT2YC7.js → chunk-UBRD5FH4.js} +9 -9
  38. package/dist/{chunk-NKQEMWGT.js → chunk-VV2PJT4K.js} +3321 -207
  39. package/dist/{chunk-JPZY7ZQX.js → chunk-Z2JORLRT.js} +1 -1
  40. package/dist/{chunk-SZ3Q4XEO.js → chunk-ZBQ3ZY75.js} +433 -283
  41. package/dist/{ci-workflow-FJYRFZYQ.js → ci-workflow-H52EMCL6.js} +3 -3
  42. package/dist/{dist-HPWNWCT6.js → dist-PGQ32ZI7.js} +41 -1
  43. package/dist/{dist-ZV6GO6FA.js → dist-TG63OKA5.js} +2 -2
  44. package/dist/{docs-7DW3DI4Z.js → docs-GP4VUSIB.js} +4 -4
  45. package/dist/{engine-P7EE2IWO.js → engine-KQG5RVXX.js} +3 -3
  46. package/dist/{entropy-HCXRTDFU.js → entropy-RXESIYKC.js} +3 -3
  47. package/dist/{feedback-Y4FYN3NR.js → feedback-HS7ZYXOU.js} +1 -1
  48. package/dist/{generate-agent-definitions-3EHPIWBO.js → generate-agent-definitions-I4B7CVOB.js} +4 -4
  49. package/dist/{graph-loader-KXVS3YK3.js → graph-loader-TIVI6NQ7.js} +1 -1
  50. package/dist/index.d.ts +8 -8
  51. package/dist/index.js +25 -25
  52. package/dist/{loader-SKHF3JVV.js → loader-CWAH6B4H.js} +3 -3
  53. package/dist/{mcp-MWYIPDQU.js → mcp-KHK5KYER.js} +15 -15
  54. package/dist/{performance-ADWH5NJY.js → performance-WDW5WS3J.js} +4 -4
  55. package/dist/{review-pipeline-TLKE5OQD.js → review-pipeline-QOZGWCTY.js} +3 -3
  56. package/dist/{runtime-7LYAW7GU.js → runtime-SFEFRPLX.js} +3 -3
  57. package/dist/{scan-BGJ7TLLV.js → scan-IJ7EYTF7.js} +1 -1
  58. package/dist/{security-5XWINYVB.js → security-2K7UUK6T.js} +1 -1
  59. package/dist/{validate-BFFHYHY7.js → validate-HXM6DXRZ.js} +4 -4
  60. package/dist/{validate-cross-check-GQX7OVCR.js → validate-cross-check-ULQLEOME.js} +3 -3
  61. package/package.json +9 -9
@@ -0,0 +1,277 @@
1
+ # Harness Knowledge Pipeline
2
+
3
+ > 4-phase knowledge extraction, reconciliation, drift detection, and remediation with convergence loop. Keeps the business knowledge graph current and identifies coverage gaps.
4
+
5
+ ## When to Use
6
+
7
+ - When you want a full knowledge health check: extract signals, detect drift, find gaps
8
+ - After adding new code, connectors, or diagram files that contain business knowledge
9
+ - As a periodic hygiene check to ensure the knowledge graph reflects the codebase
10
+ - When `--drift-check` is needed in CI to gate on knowledge freshness
11
+ - NOT for manually authoring knowledge files (write to `docs/knowledge/` directly)
12
+ - NOT for ingesting a single source (use `ingest_source` MCP tool directly)
13
+ - NOT for graph queries or exploration (use `ask_graph` or `query_graph`)
14
+
15
+ ## Process
16
+
17
+ 1. **EXTRACT:** Run code signal extractors, diagram parsers, BusinessKnowledgeIngestor, and KnowledgeLinker against the project
18
+ 2. **RECONCILE:** Build pre-extraction snapshot (current graph state) and post-extraction snapshot, then run StructuralDriftDetector
19
+ 3. **DETECT:** Partition findings by classification (new/stale/drifted/contradicting), generate gap report
20
+ 4. **REMEDIATE (only with `--fix`):** Apply safe remediations, convergence loop up to 5 iterations
21
+
22
+ ## Iron Law
23
+
24
+ **Auto-remediate stale findings only. Prompt for drifted and contradicting.** Never auto-resolve a `contradicting` finding — the human must decide which source is authoritative.
25
+
26
+ ## Flags
27
+
28
+ | Flag | Effect |
29
+ | ----------------- | ---------------------------------------------------------------- |
30
+ | `--fix` | Enable convergence-based auto-remediation (default: detect-only) |
31
+ | `--ci` | Non-interactive: apply safe fixes only, report everything else |
32
+ | `--domain <name>` | Limit pipeline to specific knowledge domain |
33
+
34
+ ## Shared Context Object
35
+
36
+ All phases read from and write to a shared `KnowledgePipelineContext`:
37
+
38
+ ```typescript
39
+ interface KnowledgePipelineContext {
40
+ extractionSnapshot: KnowledgeSnapshot;
41
+ currentSnapshot: KnowledgeSnapshot;
42
+ driftResult: DriftResult;
43
+ gapReport: GapReport;
44
+ remediationsApplied: string[];
45
+ iteration: number;
46
+ verdict: 'pass' | 'warn' | 'fail';
47
+ }
48
+ ```
49
+
50
+ ---
51
+
52
+ ## Phase 1: EXTRACT
53
+
54
+ Extract business knowledge from all available sources into a fresh snapshot.
55
+
56
+ 1. **Code Signal Extractors:** Run `ExtractionRunner` against the project directory.
57
+ - Test description extractor
58
+ - Enum/constant extractor
59
+ - Validation rule extractor
60
+ - API path extractor
61
+ - Output goes to `.harness/knowledge/extracted/`
62
+
63
+ 2. **Diagram Parsers:** Run `DiagramParser.ingest()` for diagram-as-code files.
64
+ - Scans for `.mmd`, `.mermaid`, `.d2`, `.puml`, `.plantuml` files
65
+ - Extracts entities and relationships into `business_concept` nodes
66
+
67
+ 3. **Connector Sync** (if configured): Trigger connector sync for Jira, Slack, Confluence.
68
+ - Only runs if connectors are configured in `harness.config.json`
69
+ - Skip silently if no connectors
70
+
71
+ 4. **Build Fresh Snapshot:** Collect all extraction results into a `KnowledgeSnapshot`.
72
+ - Each entry has: `id`, `type`, `contentHash`, `source`, `name`
73
+
74
+ **Output:** `context.extractionSnapshot` populated.
75
+
76
+ ---
77
+
78
+ ## Phase 2: RECONCILE
79
+
80
+ Compare the fresh extraction against the current graph state.
81
+
82
+ 1. **Build Current Snapshot:** Read all `business_*` nodes from GraphStore.
83
+ - Map each node to a `KnowledgeSnapshotEntry`
84
+ - Use node ID as entry ID, compute contentHash from node content
85
+
86
+ 2. **Run Drift Detection:** Call `StructuralDriftDetector.detect(current, fresh)`.
87
+ - Produces `DriftResult` with findings classified as `new`, `drifted`, `stale`, `contradicting`
88
+ - Produces `driftScore` (0.0 - 1.0)
89
+
90
+ **Output:** `context.currentSnapshot` and `context.driftResult` populated.
91
+
92
+ ---
93
+
94
+ ## Phase 3: DETECT
95
+
96
+ Partition drift findings and classify safety.
97
+
98
+ 1. **Partition by classification:**
99
+
100
+ | Classification | Severity | Safety | Action |
101
+ | --------------- | -------- | ------------- | ------------------------- |
102
+ | `new` | low | safe | Stage automatically |
103
+ | `stale` | high | probably-safe | Auto-remove (source gone) |
104
+ | `drifted` | medium | probably-safe | Prompt for confirmation |
105
+ | `contradicting` | critical | unsafe | Never auto-resolve |
106
+
107
+ 2. **Generate Drift Report:** Present findings grouped by classification:
108
+
109
+ ```
110
+ KNOWLEDGE PIPELINE -- Drift Detection
111
+
112
+ Drift Score: 0.23 (12 findings / 52 entries)
113
+
114
+ NEW (4 findings, safe):
115
+ - business_rule:payments:refund-window [extractor]
116
+ - business_concept:auth:session-timeout [diagram]
117
+ ...
118
+
119
+ STALE (3 findings, probably-safe):
120
+ - business_fact:billing:old-rate-limit [extractor] — source file deleted
121
+ ...
122
+
123
+ DRIFTED (4 findings, requires confirmation):
124
+ - business_rule:checkout:tax-calculation [extractor] — content changed
125
+ ...
126
+
127
+ CONTRADICTING (1 finding, requires human decision):
128
+ - business_term:Settlement SLA — extractor says 24h, linker says 48h
129
+ ```
130
+
131
+ 3. **Generate Gap Report:** Run `KnowledgeStagingAggregator.generateGapReport()`.
132
+ - Lists domains with entry counts
133
+ - Write to `.harness/knowledge/gaps.md`
134
+
135
+ **Output:** Drift report and gap report written. `context.gapReport` populated.
136
+
137
+ ---
138
+
139
+ ## Phase 4: REMEDIATE (only with `--fix`)
140
+
141
+ Apply safe fixes and converge.
142
+
143
+ 1. **Stage `new` findings:** Write to `.harness/knowledge/staged/pipeline-staged.jsonl` via `KnowledgeStagingAggregator`.
144
+
145
+ 2. **Auto-remove `stale` findings:** Remove nodes from graph where source file no longer exists.
146
+ - Log each removal
147
+
148
+ 3. **Present `drifted` findings:** Ask the human to confirm each update.
149
+ - In `--ci` mode: skip, report as unresolved
150
+ - If confirmed: update the graph node with fresh content
151
+
152
+ 4. **Surface `contradicting` findings:** Never auto-resolve.
153
+ - Present both sources and ask the human which is authoritative
154
+ - In `--ci` mode: report as unresolved
155
+
156
+ 5. **Convergence Check:** After remediation:
157
+ - Re-run EXTRACT + RECONCILE + DETECT
158
+ - Count remaining findings
159
+ - If `newCount >= previousCount`: STOP (converged or no progress)
160
+ - If `newCount < previousCount`: continue (max 5 iterations)
161
+
162
+ ### Convergence Loop
163
+
164
+ ```
165
+ maxIterations = 5
166
+ previousCount = findings.length
167
+
168
+ while iteration < maxIterations:
169
+ 1. Apply safe remediations (new → stage, stale → remove)
170
+ 2. Present probably-safe remediations (skip in --ci)
171
+ 3. Log unsafe findings (never auto-apply)
172
+ 4. Re-run EXTRACT + RECONCILE + DETECT
173
+ 5. newCount = remaining findings
174
+ 6. if newCount >= previousCount: STOP (converged)
175
+ 7. previousCount = newCount; iteration++
176
+ ```
177
+
178
+ ---
179
+
180
+ ## Verdict Rules
181
+
182
+ After all phases complete, compute verdict:
183
+
184
+ | Verdict | Condition |
185
+ | ------- | ------------------------------------------------- |
186
+ | `pass` | Zero unresolved findings after pipeline |
187
+ | `warn` | Only `new` findings remain (low severity) |
188
+ | `fail` | Any `contradicting`, `stale`, or `drifted` remain |
189
+
190
+ Present verdict summary:
191
+
192
+ ```
193
+ KNOWLEDGE PIPELINE -- Verdict: WARN
194
+
195
+ Findings: 2 new (staged), 0 stale, 0 drifted, 0 contradicting
196
+ Gap Report: 3 domains, 12 total entries
197
+ Drift Score: 0.04
198
+ ```
199
+
200
+ ## Harness Integration
201
+
202
+ - **`ingest_source`** -- MCP tool for ingesting diagram sources (`source: 'diagrams'`)
203
+ - **`ExtractionRunner`** -- Code signal extraction from `@harness-engineering/graph`
204
+ - **`DiagramParser`** -- Diagram-as-code parsing from `@harness-engineering/graph`
205
+ - **`StructuralDriftDetector`** -- Drift detection from `@harness-engineering/graph`
206
+ - **`KnowledgeStagingAggregator`** -- Staging and gap reporting from `@harness-engineering/graph`
207
+ - **`harness validate`** -- Run after remediation to verify project health
208
+
209
+ ## Success Criteria
210
+
211
+ 1. All 4 phases execute in sequence (EXTRACT, RECONCILE, DETECT, REMEDIATE)
212
+ 2. Drift detection correctly classifies findings into 4 categories
213
+ 3. Auto-remediation only applies to safe/probably-safe findings
214
+ 4. Contradicting findings are never auto-resolved
215
+ 5. Convergence loop terminates when finding count stops decreasing (max 5 iterations)
216
+ 6. Gap report lists domains with entry counts
217
+ 7. Verdict accurately reflects remaining finding state
218
+ 8. `--ci` mode is fully non-interactive
219
+
220
+ ## Examples
221
+
222
+ ### Example: Running detect-only pipeline
223
+
224
+ ```
225
+ $ harness knowledge-pipeline
226
+
227
+ KNOWLEDGE PIPELINE -- Verdict: WARN
228
+
229
+ Drift Score: 0.12
230
+ Findings: 3 new, 0 stale, 0 drifted, 0 contradicting
231
+ Extraction: 12 code signals, 5 diagrams, 2 linker facts, 4 business knowledge
232
+ Gaps: 2 domains, 16 total entries
233
+ ```
234
+
235
+ ### Example: Running with fix mode
236
+
237
+ ```
238
+ $ harness knowledge-pipeline --fix
239
+
240
+ KNOWLEDGE PIPELINE -- Verdict: PASS
241
+
242
+ Drift Score: 0.00
243
+ Findings: 0 new, 0 stale, 0 drifted, 0 contradicting
244
+ Extraction: 12 code signals, 5 diagrams, 2 linker facts, 4 business knowledge
245
+ Gaps: 2 domains, 19 total entries
246
+ Convergence: 2 iterations
247
+ Remediations: 3 applied
248
+ ```
249
+
250
+ ### Example: CI gate mode
251
+
252
+ ```
253
+ $ harness knowledge-pipeline --ci --drift-check
254
+ # Exits 1 if unresolved drift exists
255
+ ```
256
+
257
+ ## Rationalizations to Reject
258
+
259
+ | Rationalization | Reality |
260
+ | ------------------------------------------------------------------------------------ | --------------------------------------------------------------------------------------------------------------------------------------------------- |
261
+ | "The contradicting findings have an obvious resolution, so I can auto-fix them" | The Iron Law: contradicting findings require human decision. Different sources may have different authority levels that only the human understands. |
262
+ | "Drift score is low (0.05), so I can skip the DETECT phase and go straight to PASS" | Every finding must be classified regardless of drift score. A low score with one critical contradiction is still a FAIL. |
263
+ | "The stale entries might come back if the source is restored, so I should keep them" | Stale means the source is gone now. If it comes back, the next extraction will find it as NEW. Keeping stale entries pollutes the graph. |
264
+ | "I can run the convergence loop more than 5 times to get to zero findings" | The 5-iteration cap is a safety bound. If findings aren't decreasing, more iterations won't help — the remaining issues need human intervention. |
265
+
266
+ ## Gates
267
+
268
+ - **No auto-resolution of contradicting findings.** EVER. Present both sources, ask the human.
269
+ - **No skipping DETECT.** Even in `--fix` mode, DETECT must run before REMEDIATE.
270
+ - **No convergence beyond 5 iterations.** If findings aren't decreasing, stop and report.
271
+ - **No REMEDIATE without `--fix`.** Default mode is detect-and-report only.
272
+
273
+ ## Escalation
274
+
275
+ - **When no graph is available:** Run extractors and diagram parsers only. Skip reconciliation (no current snapshot). Report extraction results as gap analysis.
276
+ - **When connectors fail:** Log the error, continue with available sources. Note which connectors were skipped in the report.
277
+ - **When convergence stalls at iteration 1:** All remaining findings require human intervention. Present them and stop.
@@ -0,0 +1,60 @@
1
+ name: harness-knowledge-pipeline
2
+ version: "1.0.0"
3
+ description: 4-phase knowledge extraction, reconciliation, drift detection, and remediation with convergence loop
4
+ stability: static
5
+ cognitive_mode: constructive-architect
6
+ triggers:
7
+ - manual
8
+ platforms:
9
+ - claude-code
10
+ - gemini-cli
11
+ - cursor
12
+ - codex
13
+ tools:
14
+ - Bash
15
+ - Read
16
+ - Write
17
+ - Edit
18
+ - Glob
19
+ - Grep
20
+ cli:
21
+ command: harness skill run harness-knowledge-pipeline
22
+ args:
23
+ - name: path
24
+ description: Project root path
25
+ required: false
26
+ - name: fix
27
+ description: Enable auto-remediation of safe findings (default detect-only)
28
+ required: false
29
+ - name: ci
30
+ description: Non-interactive mode, skip probably-safe fixes
31
+ required: false
32
+ - name: domain
33
+ description: Limit pipeline to specific knowledge domain
34
+ required: false
35
+ mcp:
36
+ tool: run_skill
37
+ input:
38
+ skill: harness-knowledge-pipeline
39
+ path: string
40
+ type: rigid
41
+ tier: 2
42
+ phases:
43
+ - name: extract
44
+ description: Run code signal extractors, diagram parsers, and connector sync
45
+ required: true
46
+ - name: reconcile
47
+ description: Build snapshots and run structural drift detection
48
+ required: true
49
+ - name: detect
50
+ description: Partition findings by severity and safety classification
51
+ required: true
52
+ - name: remediate
53
+ description: Apply safe fixes, prompt for unsafe, convergence loop
54
+ required: false
55
+ state:
56
+ persistent: false
57
+ files:
58
+ - .harness/knowledge/staged/pipeline-staged.jsonl
59
+ - .harness/knowledge/gaps.md
60
+ depends_on: []
@@ -0,0 +1,277 @@
1
+ # Harness Knowledge Pipeline
2
+
3
+ > 4-phase knowledge extraction, reconciliation, drift detection, and remediation with convergence loop. Keeps the business knowledge graph current and identifies coverage gaps.
4
+
5
+ ## When to Use
6
+
7
+ - When you want a full knowledge health check: extract signals, detect drift, find gaps
8
+ - After adding new code, connectors, or diagram files that contain business knowledge
9
+ - As a periodic hygiene check to ensure the knowledge graph reflects the codebase
10
+ - When `--drift-check` is needed in CI to gate on knowledge freshness
11
+ - NOT for manually authoring knowledge files (write to `docs/knowledge/` directly)
12
+ - NOT for ingesting a single source (use `ingest_source` MCP tool directly)
13
+ - NOT for graph queries or exploration (use `ask_graph` or `query_graph`)
14
+
15
+ ## Process
16
+
17
+ 1. **EXTRACT:** Run code signal extractors, diagram parsers, BusinessKnowledgeIngestor, and KnowledgeLinker against the project
18
+ 2. **RECONCILE:** Build pre-extraction snapshot (current graph state) and post-extraction snapshot, then run StructuralDriftDetector
19
+ 3. **DETECT:** Partition findings by classification (new/stale/drifted/contradicting), generate gap report
20
+ 4. **REMEDIATE (only with `--fix`):** Apply safe remediations, convergence loop up to 5 iterations
21
+
22
+ ## Iron Law
23
+
24
+ **Auto-remediate stale findings only. Prompt for drifted and contradicting.** Never auto-resolve a `contradicting` finding — the human must decide which source is authoritative.
25
+
26
+ ## Flags
27
+
28
+ | Flag | Effect |
29
+ | ----------------- | ---------------------------------------------------------------- |
30
+ | `--fix` | Enable convergence-based auto-remediation (default: detect-only) |
31
+ | `--ci` | Non-interactive: apply safe fixes only, report everything else |
32
+ | `--domain <name>` | Limit pipeline to specific knowledge domain |
33
+
34
+ ## Shared Context Object
35
+
36
+ All phases read from and write to a shared `KnowledgePipelineContext`:
37
+
38
+ ```typescript
39
+ interface KnowledgePipelineContext {
40
+ extractionSnapshot: KnowledgeSnapshot;
41
+ currentSnapshot: KnowledgeSnapshot;
42
+ driftResult: DriftResult;
43
+ gapReport: GapReport;
44
+ remediationsApplied: string[];
45
+ iteration: number;
46
+ verdict: 'pass' | 'warn' | 'fail';
47
+ }
48
+ ```
49
+
50
+ ---
51
+
52
+ ## Phase 1: EXTRACT
53
+
54
+ Extract business knowledge from all available sources into a fresh snapshot.
55
+
56
+ 1. **Code Signal Extractors:** Run `ExtractionRunner` against the project directory.
57
+ - Test description extractor
58
+ - Enum/constant extractor
59
+ - Validation rule extractor
60
+ - API path extractor
61
+ - Output goes to `.harness/knowledge/extracted/`
62
+
63
+ 2. **Diagram Parsers:** Run `DiagramParser.ingest()` for diagram-as-code files.
64
+ - Scans for `.mmd`, `.mermaid`, `.d2`, `.puml`, `.plantuml` files
65
+ - Extracts entities and relationships into `business_concept` nodes
66
+
67
+ 3. **Connector Sync** (if configured): Trigger connector sync for Jira, Slack, Confluence.
68
+ - Only runs if connectors are configured in `harness.config.json`
69
+ - Skip silently if no connectors
70
+
71
+ 4. **Build Fresh Snapshot:** Collect all extraction results into a `KnowledgeSnapshot`.
72
+ - Each entry has: `id`, `type`, `contentHash`, `source`, `name`
73
+
74
+ **Output:** `context.extractionSnapshot` populated.
75
+
76
+ ---
77
+
78
+ ## Phase 2: RECONCILE
79
+
80
+ Compare the fresh extraction against the current graph state.
81
+
82
+ 1. **Build Current Snapshot:** Read all `business_*` nodes from GraphStore.
83
+ - Map each node to a `KnowledgeSnapshotEntry`
84
+ - Use node ID as entry ID, compute contentHash from node content
85
+
86
+ 2. **Run Drift Detection:** Call `StructuralDriftDetector.detect(current, fresh)`.
87
+ - Produces `DriftResult` with findings classified as `new`, `drifted`, `stale`, `contradicting`
88
+ - Produces `driftScore` (0.0 - 1.0)
89
+
90
+ **Output:** `context.currentSnapshot` and `context.driftResult` populated.
91
+
92
+ ---
93
+
94
+ ## Phase 3: DETECT
95
+
96
+ Partition drift findings and classify safety.
97
+
98
+ 1. **Partition by classification:**
99
+
100
+ | Classification | Severity | Safety | Action |
101
+ | --------------- | -------- | ------------- | ------------------------- |
102
+ | `new` | low | safe | Stage automatically |
103
+ | `stale` | high | probably-safe | Auto-remove (source gone) |
104
+ | `drifted` | medium | probably-safe | Prompt for confirmation |
105
+ | `contradicting` | critical | unsafe | Never auto-resolve |
106
+
107
+ 2. **Generate Drift Report:** Present findings grouped by classification:
108
+
109
+ ```
110
+ KNOWLEDGE PIPELINE -- Drift Detection
111
+
112
+ Drift Score: 0.23 (12 findings / 52 entries)
113
+
114
+ NEW (4 findings, safe):
115
+ - business_rule:payments:refund-window [extractor]
116
+ - business_concept:auth:session-timeout [diagram]
117
+ ...
118
+
119
+ STALE (3 findings, probably-safe):
120
+ - business_fact:billing:old-rate-limit [extractor] — source file deleted
121
+ ...
122
+
123
+ DRIFTED (4 findings, requires confirmation):
124
+ - business_rule:checkout:tax-calculation [extractor] — content changed
125
+ ...
126
+
127
+ CONTRADICTING (1 finding, requires human decision):
128
+ - business_term:Settlement SLA — extractor says 24h, linker says 48h
129
+ ```
130
+
131
+ 3. **Generate Gap Report:** Run `KnowledgeStagingAggregator.generateGapReport()`.
132
+ - Lists domains with entry counts
133
+ - Write to `.harness/knowledge/gaps.md`
134
+
135
+ **Output:** Drift report and gap report written. `context.gapReport` populated.
136
+
137
+ ---
138
+
139
+ ## Phase 4: REMEDIATE (only with `--fix`)
140
+
141
+ Apply safe fixes and converge.
142
+
143
+ 1. **Stage `new` findings:** Write to `.harness/knowledge/staged/pipeline-staged.jsonl` via `KnowledgeStagingAggregator`.
144
+
145
+ 2. **Auto-remove `stale` findings:** Remove nodes from graph where source file no longer exists.
146
+ - Log each removal
147
+
148
+ 3. **Present `drifted` findings:** Ask the human to confirm each update.
149
+ - In `--ci` mode: skip, report as unresolved
150
+ - If confirmed: update the graph node with fresh content
151
+
152
+ 4. **Surface `contradicting` findings:** Never auto-resolve.
153
+ - Present both sources and ask the human which is authoritative
154
+ - In `--ci` mode: report as unresolved
155
+
156
+ 5. **Convergence Check:** After remediation:
157
+ - Re-run EXTRACT + RECONCILE + DETECT
158
+ - Count remaining findings
159
+ - If `newCount >= previousCount`: STOP (converged or no progress)
160
+ - If `newCount < previousCount`: continue (max 5 iterations)
161
+
162
+ ### Convergence Loop
163
+
164
+ ```
165
+ maxIterations = 5
166
+ previousCount = findings.length
167
+
168
+ while iteration < maxIterations:
169
+ 1. Apply safe remediations (new → stage, stale → remove)
170
+ 2. Present probably-safe remediations (skip in --ci)
171
+ 3. Log unsafe findings (never auto-apply)
172
+ 4. Re-run EXTRACT + RECONCILE + DETECT
173
+ 5. newCount = remaining findings
174
+ 6. if newCount >= previousCount: STOP (converged)
175
+ 7. previousCount = newCount; iteration++
176
+ ```
177
+
178
+ ---
179
+
180
+ ## Verdict Rules
181
+
182
+ After all phases complete, compute verdict:
183
+
184
+ | Verdict | Condition |
185
+ | ------- | ------------------------------------------------- |
186
+ | `pass` | Zero unresolved findings after pipeline |
187
+ | `warn` | Only `new` findings remain (low severity) |
188
+ | `fail` | Any `contradicting`, `stale`, or `drifted` remain |
189
+
190
+ Present verdict summary:
191
+
192
+ ```
193
+ KNOWLEDGE PIPELINE -- Verdict: WARN
194
+
195
+ Findings: 2 new (staged), 0 stale, 0 drifted, 0 contradicting
196
+ Gap Report: 3 domains, 12 total entries
197
+ Drift Score: 0.04
198
+ ```
199
+
200
+ ## Harness Integration
201
+
202
+ - **`ingest_source`** -- MCP tool for ingesting diagram sources (`source: 'diagrams'`)
203
+ - **`ExtractionRunner`** -- Code signal extraction from `@harness-engineering/graph`
204
+ - **`DiagramParser`** -- Diagram-as-code parsing from `@harness-engineering/graph`
205
+ - **`StructuralDriftDetector`** -- Drift detection from `@harness-engineering/graph`
206
+ - **`KnowledgeStagingAggregator`** -- Staging and gap reporting from `@harness-engineering/graph`
207
+ - **`harness validate`** -- Run after remediation to verify project health
208
+
209
+ ## Success Criteria
210
+
211
+ 1. All 4 phases execute in sequence (EXTRACT, RECONCILE, DETECT, REMEDIATE)
212
+ 2. Drift detection correctly classifies findings into 4 categories
213
+ 3. Auto-remediation only applies to safe/probably-safe findings
214
+ 4. Contradicting findings are never auto-resolved
215
+ 5. Convergence loop terminates when finding count stops decreasing (max 5 iterations)
216
+ 6. Gap report lists domains with entry counts
217
+ 7. Verdict accurately reflects remaining finding state
218
+ 8. `--ci` mode is fully non-interactive
219
+
220
+ ## Examples
221
+
222
+ ### Example: Running detect-only pipeline
223
+
224
+ ```
225
+ $ harness knowledge-pipeline
226
+
227
+ KNOWLEDGE PIPELINE -- Verdict: WARN
228
+
229
+ Drift Score: 0.12
230
+ Findings: 3 new, 0 stale, 0 drifted, 0 contradicting
231
+ Extraction: 12 code signals, 5 diagrams, 2 linker facts, 4 business knowledge
232
+ Gaps: 2 domains, 16 total entries
233
+ ```
234
+
235
+ ### Example: Running with fix mode
236
+
237
+ ```
238
+ $ harness knowledge-pipeline --fix
239
+
240
+ KNOWLEDGE PIPELINE -- Verdict: PASS
241
+
242
+ Drift Score: 0.00
243
+ Findings: 0 new, 0 stale, 0 drifted, 0 contradicting
244
+ Extraction: 12 code signals, 5 diagrams, 2 linker facts, 4 business knowledge
245
+ Gaps: 2 domains, 19 total entries
246
+ Convergence: 2 iterations
247
+ Remediations: 3 applied
248
+ ```
249
+
250
+ ### Example: CI gate mode
251
+
252
+ ```
253
+ $ harness knowledge-pipeline --ci --drift-check
254
+ # Exits 1 if unresolved drift exists
255
+ ```
256
+
257
+ ## Rationalizations to Reject
258
+
259
+ | Rationalization | Reality |
260
+ | ------------------------------------------------------------------------------------ | --------------------------------------------------------------------------------------------------------------------------------------------------- |
261
+ | "The contradicting findings have an obvious resolution, so I can auto-fix them" | The Iron Law: contradicting findings require human decision. Different sources may have different authority levels that only the human understands. |
262
+ | "Drift score is low (0.05), so I can skip the DETECT phase and go straight to PASS" | Every finding must be classified regardless of drift score. A low score with one critical contradiction is still a FAIL. |
263
+ | "The stale entries might come back if the source is restored, so I should keep them" | Stale means the source is gone now. If it comes back, the next extraction will find it as NEW. Keeping stale entries pollutes the graph. |
264
+ | "I can run the convergence loop more than 5 times to get to zero findings" | The 5-iteration cap is a safety bound. If findings aren't decreasing, more iterations won't help — the remaining issues need human intervention. |
265
+
266
+ ## Gates
267
+
268
+ - **No auto-resolution of contradicting findings.** EVER. Present both sources, ask the human.
269
+ - **No skipping DETECT.** Even in `--fix` mode, DETECT must run before REMEDIATE.
270
+ - **No convergence beyond 5 iterations.** If findings aren't decreasing, stop and report.
271
+ - **No REMEDIATE without `--fix`.** Default mode is detect-and-report only.
272
+
273
+ ## Escalation
274
+
275
+ - **When no graph is available:** Run extractors and diagram parsers only. Skip reconciliation (no current snapshot). Report extraction results as gap analysis.
276
+ - **When connectors fail:** Log the error, continue with available sources. Note which connectors were skipped in the report.
277
+ - **When convergence stalls at iteration 1:** All remaining findings require human intervention. Present them and stop.
@@ -0,0 +1,60 @@
1
+ name: harness-knowledge-pipeline
2
+ version: "1.0.0"
3
+ description: 4-phase knowledge extraction, reconciliation, drift detection, and remediation with convergence loop
4
+ stability: static
5
+ cognitive_mode: constructive-architect
6
+ triggers:
7
+ - manual
8
+ platforms:
9
+ - claude-code
10
+ - gemini-cli
11
+ - cursor
12
+ - codex
13
+ tools:
14
+ - Bash
15
+ - Read
16
+ - Write
17
+ - Edit
18
+ - Glob
19
+ - Grep
20
+ cli:
21
+ command: harness skill run harness-knowledge-pipeline
22
+ args:
23
+ - name: path
24
+ description: Project root path
25
+ required: false
26
+ - name: fix
27
+ description: Enable auto-remediation of safe findings (default detect-only)
28
+ required: false
29
+ - name: ci
30
+ description: Non-interactive mode, skip probably-safe fixes
31
+ required: false
32
+ - name: domain
33
+ description: Limit pipeline to specific knowledge domain
34
+ required: false
35
+ mcp:
36
+ tool: run_skill
37
+ input:
38
+ skill: harness-knowledge-pipeline
39
+ path: string
40
+ type: rigid
41
+ tier: 2
42
+ phases:
43
+ - name: extract
44
+ description: Run code signal extractors, diagram parsers, and connector sync
45
+ required: true
46
+ - name: reconcile
47
+ description: Build snapshots and run structural drift detection
48
+ required: true
49
+ - name: detect
50
+ description: Partition findings by severity and safety classification
51
+ required: true
52
+ - name: remediate
53
+ description: Apply safe fixes, prompt for unsafe, convergence loop
54
+ required: false
55
+ state:
56
+ persistent: false
57
+ files:
58
+ - .harness/knowledge/staged/pipeline-staged.jsonl
59
+ - .harness/knowledge/gaps.md
60
+ depends_on: []