@theglitchking/hit-em-with-the-docs 2.1.1 → 2.3.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/.claude-plugin/marketplace.json +2 -2
- package/.claude-plugin/plugin.json +1 -1
- package/README.md +5 -0
- package/commands/audit-facts.md +25 -0
- package/commands/cite.md +17 -0
- package/commands/extract-facts.md +66 -0
- package/commands/find-citers.md +16 -0
- package/commands/help.md +86 -0
- package/commands/migrate-incident.md +18 -0
- package/dist/action/core/audit/auditor.d.ts +14 -0
- package/dist/action/core/audit/auditor.d.ts.map +1 -1
- package/dist/action/core/domains/classifier.d.ts +15 -1
- package/dist/action/core/domains/classifier.d.ts.map +1 -1
- package/dist/action/core/knowledge-base/audit.d.ts +67 -0
- package/dist/action/core/knowledge-base/audit.d.ts.map +1 -0
- package/dist/action/core/knowledge-base/cite.d.ts +41 -0
- package/dist/action/core/knowledge-base/cite.d.ts.map +1 -0
- package/dist/action/core/knowledge-base/citers.d.ts +119 -0
- package/dist/action/core/knowledge-base/citers.d.ts.map +1 -0
- package/dist/action/core/knowledge-base/extract.d.ts +61 -0
- package/dist/action/core/knowledge-base/extract.d.ts.map +1 -0
- package/dist/action/core/knowledge-base/migrate.d.ts +33 -0
- package/dist/action/core/knowledge-base/migrate.d.ts.map +1 -0
- package/dist/action/core/maintain/orchestrator.d.ts.map +1 -1
- package/dist/action/core/metadata/errors.d.ts +62 -0
- package/dist/action/core/metadata/errors.d.ts.map +1 -0
- package/dist/action/core/metadata/schema.d.ts +810 -49
- package/dist/action/core/metadata/schema.d.ts.map +1 -1
- package/dist/action/generators/facts-index.d.ts +27 -0
- package/dist/action/generators/facts-index.d.ts.map +1 -0
- package/dist/action/generators/incidents-index.d.ts +21 -0
- package/dist/action/generators/incidents-index.d.ts.map +1 -0
- package/dist/action/generators/symptoms-index.d.ts +20 -0
- package/dist/action/generators/symptoms-index.d.ts.map +1 -0
- package/dist/action/generators/table.d.ts +8 -0
- package/dist/action/generators/table.d.ts.map +1 -0
- package/dist/action/index.d.ts +7 -0
- package/dist/action/index.d.ts.map +1 -1
- package/dist/action/index.js +4 -4
- package/dist/action/utils/config.d.ts +99 -0
- package/dist/action/utils/config.d.ts.map +1 -0
- package/dist/cli/index.js +248 -1
- package/dist/cli/index.js.map +1 -1
- package/dist/core/audit/auditor.d.ts +14 -0
- package/dist/core/audit/auditor.d.ts.map +1 -1
- package/dist/core/audit/auditor.js +19 -3
- package/dist/core/audit/auditor.js.map +1 -1
- package/dist/core/domains/classifier.d.ts +15 -1
- package/dist/core/domains/classifier.d.ts.map +1 -1
- package/dist/core/domains/classifier.js +100 -1
- package/dist/core/domains/classifier.js.map +1 -1
- package/dist/core/knowledge-base/audit.d.ts +67 -0
- package/dist/core/knowledge-base/audit.d.ts.map +1 -0
- package/dist/core/knowledge-base/audit.js +158 -0
- package/dist/core/knowledge-base/audit.js.map +1 -0
- package/dist/core/knowledge-base/cite.d.ts +41 -0
- package/dist/core/knowledge-base/cite.d.ts.map +1 -0
- package/dist/core/knowledge-base/cite.js +82 -0
- package/dist/core/knowledge-base/cite.js.map +1 -0
- package/dist/core/knowledge-base/citers.d.ts +119 -0
- package/dist/core/knowledge-base/citers.d.ts.map +1 -0
- package/dist/core/knowledge-base/citers.js +249 -0
- package/dist/core/knowledge-base/citers.js.map +1 -0
- package/dist/core/knowledge-base/extract.d.ts +61 -0
- package/dist/core/knowledge-base/extract.d.ts.map +1 -0
- package/dist/core/knowledge-base/extract.js +132 -0
- package/dist/core/knowledge-base/extract.js.map +1 -0
- package/dist/core/knowledge-base/migrate.d.ts +33 -0
- package/dist/core/knowledge-base/migrate.d.ts.map +1 -0
- package/dist/core/knowledge-base/migrate.js +112 -0
- package/dist/core/knowledge-base/migrate.js.map +1 -0
- package/dist/core/maintain/orchestrator.d.ts.map +1 -1
- package/dist/core/maintain/orchestrator.js +48 -1
- package/dist/core/maintain/orchestrator.js.map +1 -1
- package/dist/core/metadata/errors.d.ts +62 -0
- package/dist/core/metadata/errors.d.ts.map +1 -0
- package/dist/core/metadata/errors.js +95 -0
- package/dist/core/metadata/errors.js.map +1 -0
- package/dist/core/metadata/schema.d.ts +806 -45
- package/dist/core/metadata/schema.d.ts.map +1 -1
- package/dist/core/metadata/schema.js +472 -42
- package/dist/core/metadata/schema.js.map +1 -1
- package/dist/generators/facts-index.d.ts +27 -0
- package/dist/generators/facts-index.d.ts.map +1 -0
- package/dist/generators/facts-index.js +111 -0
- package/dist/generators/facts-index.js.map +1 -0
- package/dist/generators/incidents-index.d.ts +21 -0
- package/dist/generators/incidents-index.d.ts.map +1 -0
- package/dist/generators/incidents-index.js +79 -0
- package/dist/generators/incidents-index.js.map +1 -0
- package/dist/generators/symptoms-index.d.ts +20 -0
- package/dist/generators/symptoms-index.d.ts.map +1 -0
- package/dist/generators/symptoms-index.js +123 -0
- package/dist/generators/symptoms-index.js.map +1 -0
- package/dist/generators/table.d.ts +8 -0
- package/dist/generators/table.d.ts.map +1 -0
- package/dist/generators/table.js +23 -0
- package/dist/generators/table.js.map +1 -0
- package/dist/index.d.ts +7 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +8 -0
- package/dist/index.js.map +1 -1
- package/dist/utils/config.d.ts +99 -0
- package/dist/utils/config.d.ts.map +1 -0
- package/dist/utils/config.js +95 -0
- package/dist/utils/config.js.map +1 -0
- package/package.json +1 -1
- package/templates/knowledge-base/README.md +31 -0
- package/templates/knowledge-base/fact.template.md +44 -0
- package/templates/knowledge-base/incident-facts.template.md +31 -0
- package/templates/knowledge-base/incident-narrative.template.md +50 -0
- package/templates/knowledge-base/playbook-symptoms.template.md +74 -0
|
@@ -2,7 +2,38 @@
|
|
|
2
2
|
* Document tier classification system.
|
|
3
3
|
* Classifies documents into 5 tiers based on content structure.
|
|
4
4
|
*/
|
|
5
|
-
export const TIERS = [
|
|
5
|
+
export const TIERS = [
|
|
6
|
+
'guide',
|
|
7
|
+
'standard',
|
|
8
|
+
'example',
|
|
9
|
+
'reference',
|
|
10
|
+
'admin',
|
|
11
|
+
'plan',
|
|
12
|
+
'fact',
|
|
13
|
+
'incident-narrative',
|
|
14
|
+
'incident-facts',
|
|
15
|
+
];
|
|
16
|
+
/**
|
|
17
|
+
* Tiers that use lifecycle status (status field) instead of semver versioning.
|
|
18
|
+
* These tiers have `version` relaxed to optional in the MetadataSchema and
|
|
19
|
+
* accept tier-specific status enums in addition to (or instead of) the
|
|
20
|
+
* doc-tier status enum.
|
|
21
|
+
*
|
|
22
|
+
* - plan: phase/task/atom planning artifacts (added in 2.2.0)
|
|
23
|
+
* - fact: atomic knowledge claims, tracked via `last_verified` + confidence
|
|
24
|
+
* - incident-narrative: postmortem story (date-stamped, immutable)
|
|
25
|
+
* - incident-facts: bridge doc linking incidents to facts they produced
|
|
26
|
+
*/
|
|
27
|
+
export const LIFECYCLE_TRACKED_TIERS = [
|
|
28
|
+
'plan',
|
|
29
|
+
'fact',
|
|
30
|
+
'incident-narrative',
|
|
31
|
+
'incident-facts',
|
|
32
|
+
];
|
|
33
|
+
export function isLifecycleTrackedTier(tier) {
|
|
34
|
+
return (typeof tier === 'string' &&
|
|
35
|
+
LIFECYCLE_TRACKED_TIERS.includes(tier));
|
|
36
|
+
}
|
|
6
37
|
export const TIER_DEFINITIONS = {
|
|
7
38
|
guide: {
|
|
8
39
|
id: 'guide',
|
|
@@ -83,6 +114,70 @@ export const TIER_DEFINITIONS = {
|
|
|
83
114
|
/^#+\s*(troubleshooting|debugging)/i,
|
|
84
115
|
],
|
|
85
116
|
},
|
|
117
|
+
plan: {
|
|
118
|
+
id: 'plan',
|
|
119
|
+
name: 'Plan',
|
|
120
|
+
description: 'Phase/task/atom planning artifacts (added in 2.2.0 for persistent-planning lg-mode interop). Plans typically carry tier: plan in frontmatter; auto-classification is a fallback.',
|
|
121
|
+
sizeRange: { min: 1, max: 200 },
|
|
122
|
+
indicators: [
|
|
123
|
+
'phase', 'task', 'atom', 'milestone', 'deliverable',
|
|
124
|
+
'plan', 'roadmap', 'blocker', 'dependency', 'next concrete action',
|
|
125
|
+
],
|
|
126
|
+
headingPatterns: [
|
|
127
|
+
/^#+\s*(goal|scope|status)/i,
|
|
128
|
+
/^#+\s*(phases?|tasks?|atoms?)/i,
|
|
129
|
+
/^#+\s*(decisions? made|errors? encountered)/i,
|
|
130
|
+
/^#+\s*(implementation notes|key questions)/i,
|
|
131
|
+
],
|
|
132
|
+
},
|
|
133
|
+
fact: {
|
|
134
|
+
id: 'fact',
|
|
135
|
+
name: 'Fact',
|
|
136
|
+
description: 'Atomic, single-claim, citable unit of knowledge (added in 2.3.0). Facts use last_verified + confidence instead of semver versioning. Facts typically carry tier: fact in frontmatter; auto-classification is a fallback.',
|
|
137
|
+
sizeRange: { min: 1, max: 5 },
|
|
138
|
+
indicators: [
|
|
139
|
+
'claim', 'confidence', 'verify', 'last verified', 'provenance',
|
|
140
|
+
'citation', 'fact', 'hypothesis', 'invalidated by', 'consequence',
|
|
141
|
+
],
|
|
142
|
+
headingPatterns: [
|
|
143
|
+
/^#+\s*(claim|the claim)/i,
|
|
144
|
+
/^#+\s*(how to verify|verification)/i,
|
|
145
|
+
/^#+\s*(consequences?|implications?)/i,
|
|
146
|
+
/^#+\s*(cited by|provenance)/i,
|
|
147
|
+
],
|
|
148
|
+
},
|
|
149
|
+
'incident-narrative': {
|
|
150
|
+
id: 'incident-narrative',
|
|
151
|
+
name: 'Incident narrative',
|
|
152
|
+
description: 'Immutable postmortem story (added in 2.3.0). Lives at <vault-root>/incidents/<date-slug>/narrative.md. Date-stamped; uses lifecycle status (open/partial/resolved/planned) not semver.',
|
|
153
|
+
sizeRange: { min: 2, max: 50 },
|
|
154
|
+
indicators: [
|
|
155
|
+
'postmortem', 'incident', 'outage', 'severity', 'resolution',
|
|
156
|
+
'timeline', 'root cause', 'remediation', 'symptoms', 'on-call',
|
|
157
|
+
],
|
|
158
|
+
headingPatterns: [
|
|
159
|
+
/^#+\s*(timeline|sequence of events)/i,
|
|
160
|
+
/^#+\s*(root cause|cause)/i,
|
|
161
|
+
/^#+\s*(impact|severity)/i,
|
|
162
|
+
/^#+\s*(remediation|resolution|fix)/i,
|
|
163
|
+
/^#+\s*(lessons learned|action items|follow[-\s]ups?)/i,
|
|
164
|
+
],
|
|
165
|
+
},
|
|
166
|
+
'incident-facts': {
|
|
167
|
+
id: 'incident-facts',
|
|
168
|
+
name: 'Incident facts bridge',
|
|
169
|
+
description: 'Bridge document linking an incident to the facts it produced, strengthened, or weakened (added in 2.3.0). Lives at <vault-root>/incidents/<date-slug>/facts.md.',
|
|
170
|
+
sizeRange: { min: 1, max: 10 },
|
|
171
|
+
indicators: [
|
|
172
|
+
'produced', 'strengthened', 'weakened', 'facts from',
|
|
173
|
+
'incident facts', 'bridges to', 'derived from',
|
|
174
|
+
],
|
|
175
|
+
headingPatterns: [
|
|
176
|
+
/^#+\s*(produced|new facts)/i,
|
|
177
|
+
/^#+\s*(strengthened)/i,
|
|
178
|
+
/^#+\s*(weakened|invalidated)/i,
|
|
179
|
+
],
|
|
180
|
+
},
|
|
86
181
|
};
|
|
87
182
|
/**
|
|
88
183
|
* Classify document content into a tier
|
|
@@ -94,6 +189,10 @@ export function classifyTier(content) {
|
|
|
94
189
|
example: 0,
|
|
95
190
|
reference: 0,
|
|
96
191
|
admin: 0,
|
|
192
|
+
plan: 0,
|
|
193
|
+
fact: 0,
|
|
194
|
+
'incident-narrative': 0,
|
|
195
|
+
'incident-facts': 0,
|
|
97
196
|
};
|
|
98
197
|
const reasoning = [];
|
|
99
198
|
const lowerContent = content.toLowerCase();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"classifier.js","sourceRoot":"","sources":["../../../src/core/domains/classifier.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,MAAM,CAAC,MAAM,KAAK,GAAG,
|
|
1
|
+
{"version":3,"file":"classifier.js","sourceRoot":"","sources":["../../../src/core/domains/classifier.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Stale-fact detection + verify-command execution (2.3.0 PR3).
|
|
3
|
+
*
|
|
4
|
+
* `auditFacts()` is the writer side of `hewtd audit-facts` — pure-data,
|
|
5
|
+
* easy to unit-test with date injection. `runFactVerify()` actually
|
|
6
|
+
* shells out and updates `last_verified` on success.
|
|
7
|
+
*
|
|
8
|
+
* Working-dir resolution (locked in during planning):
|
|
9
|
+
* - Default: `<vault-root>/facts/`
|
|
10
|
+
* - Override: a fact's optional `working_dir:` frontmatter field
|
|
11
|
+
*/
|
|
12
|
+
import type { FactRef, CiterIndex } from './citers.js';
|
|
13
|
+
export interface StaleFact {
|
|
14
|
+
id: string;
|
|
15
|
+
path: string;
|
|
16
|
+
relPath: string;
|
|
17
|
+
title: string;
|
|
18
|
+
confidence: string | undefined;
|
|
19
|
+
lastVerified: string;
|
|
20
|
+
daysSinceVerified: number;
|
|
21
|
+
}
|
|
22
|
+
export interface AuditFactsOptions {
|
|
23
|
+
index: CiterIndex;
|
|
24
|
+
/** Reference date for "now". Defaults to today. Tests inject a fixed date. */
|
|
25
|
+
now?: Date;
|
|
26
|
+
/** Stale threshold in days. Defaults to 90. */
|
|
27
|
+
auditWindowDays?: number;
|
|
28
|
+
}
|
|
29
|
+
export interface AuditFactsResult {
|
|
30
|
+
stale: StaleFact[];
|
|
31
|
+
/** Facts whose last_verified is malformed or absent. Reported but not "stale". */
|
|
32
|
+
unverifiable: FactRef[];
|
|
33
|
+
}
|
|
34
|
+
export declare function auditFacts(options: AuditFactsOptions): AuditFactsResult;
|
|
35
|
+
export interface RunVerifyOptions {
|
|
36
|
+
fact: FactRef;
|
|
37
|
+
/** Absolute vault root (used to compute default CWD). */
|
|
38
|
+
vaultRoot: string;
|
|
39
|
+
/** Override CWD (test seam). */
|
|
40
|
+
cwdOverride?: string;
|
|
41
|
+
/** Inject a fake date for the `last_verified` rewrite. */
|
|
42
|
+
now?: Date;
|
|
43
|
+
/** Skip the actual shell-out (test seam). Returns success without running. */
|
|
44
|
+
skipExec?: boolean;
|
|
45
|
+
}
|
|
46
|
+
export interface RunVerifyResult {
|
|
47
|
+
factId: string;
|
|
48
|
+
executed: boolean;
|
|
49
|
+
exitCode: number | null;
|
|
50
|
+
stdout: string;
|
|
51
|
+
stderr: string;
|
|
52
|
+
/** True iff the fact's `last_verified` was updated. */
|
|
53
|
+
updated: boolean;
|
|
54
|
+
/** YYYY-MM-DD that was written. */
|
|
55
|
+
newLastVerified: string | undefined;
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* Execute a fact's `verify_command` and update `last_verified` on success.
|
|
59
|
+
* Returns a typed result describing what happened.
|
|
60
|
+
*
|
|
61
|
+
* The verify command runs in a child shell (bash via `-c`). CWD resolution:
|
|
62
|
+
* 1. `cwdOverride` (test seam)
|
|
63
|
+
* 2. Fact's frontmatter `working_dir:` field, resolved relative to vaultRoot
|
|
64
|
+
* 3. `<vaultRoot>/facts/` default
|
|
65
|
+
*/
|
|
66
|
+
export declare function runFactVerify(options: RunVerifyOptions): Promise<RunVerifyResult>;
|
|
67
|
+
//# sourceMappingURL=audit.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"audit.d.ts","sourceRoot":"","sources":["../../../src/core/knowledge-base/audit.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAOH,OAAO,KAAK,EAAE,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAEvD,MAAM,WAAW,SAAS;IACxB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;IACd,UAAU,EAAE,MAAM,GAAG,SAAS,CAAC;IAC/B,YAAY,EAAE,MAAM,CAAC;IACrB,iBAAiB,EAAE,MAAM,CAAC;CAC3B;AAED,MAAM,WAAW,iBAAiB;IAChC,KAAK,EAAE,UAAU,CAAC;IAClB,8EAA8E;IAC9E,GAAG,CAAC,EAAE,IAAI,CAAC;IACX,+CAA+C;IAC/C,eAAe,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,SAAS,EAAE,CAAC;IACnB,kFAAkF;IAClF,YAAY,EAAE,OAAO,EAAE,CAAC;CACzB;AAED,wBAAgB,UAAU,CAAC,OAAO,EAAE,iBAAiB,GAAG,gBAAgB,CA2CvE;AAED,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,OAAO,CAAC;IACd,yDAAyD;IACzD,SAAS,EAAE,MAAM,CAAC;IAClB,gCAAgC;IAChC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,0DAA0D;IAC1D,GAAG,CAAC,EAAE,IAAI,CAAC;IACX,8EAA8E;IAC9E,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB;AAED,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,OAAO,CAAC;IAClB,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,uDAAuD;IACvD,OAAO,EAAE,OAAO,CAAC;IACjB,mCAAmC;IACnC,eAAe,EAAE,MAAM,GAAG,SAAS,CAAC;CACrC;AAED;;;;;;;;GAQG;AACH,wBAAsB,aAAa,CACjC,OAAO,EAAE,gBAAgB,GACxB,OAAO,CAAC,eAAe,CAAC,CAuE1B"}
|
|
@@ -0,0 +1,158 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Stale-fact detection + verify-command execution (2.3.0 PR3).
|
|
3
|
+
*
|
|
4
|
+
* `auditFacts()` is the writer side of `hewtd audit-facts` — pure-data,
|
|
5
|
+
* easy to unit-test with date injection. `runFactVerify()` actually
|
|
6
|
+
* shells out and updates `last_verified` on success.
|
|
7
|
+
*
|
|
8
|
+
* Working-dir resolution (locked in during planning):
|
|
9
|
+
* - Default: `<vault-root>/facts/`
|
|
10
|
+
* - Override: a fact's optional `working_dir:` frontmatter field
|
|
11
|
+
*/
|
|
12
|
+
import { readFile, writeFile } from 'fs/promises';
|
|
13
|
+
import { existsSync } from 'fs';
|
|
14
|
+
import { spawn } from 'child_process';
|
|
15
|
+
import { resolve } from 'path';
|
|
16
|
+
import matter from 'gray-matter';
|
|
17
|
+
export function auditFacts(options) {
|
|
18
|
+
const { index, now = new Date(), auditWindowDays = 90 } = options;
|
|
19
|
+
const cutoffMs = now.getTime() - auditWindowDays * 24 * 60 * 60 * 1000;
|
|
20
|
+
const stale = [];
|
|
21
|
+
const unverifiable = [];
|
|
22
|
+
for (const fact of index.facts.values()) {
|
|
23
|
+
if (!fact.lastVerified) {
|
|
24
|
+
unverifiable.push(fact);
|
|
25
|
+
continue;
|
|
26
|
+
}
|
|
27
|
+
const verifiedMs = new Date(`${fact.lastVerified}T00:00:00Z`).getTime();
|
|
28
|
+
if (Number.isNaN(verifiedMs)) {
|
|
29
|
+
unverifiable.push(fact);
|
|
30
|
+
continue;
|
|
31
|
+
}
|
|
32
|
+
if (verifiedMs < cutoffMs) {
|
|
33
|
+
const daysSinceVerified = Math.floor((now.getTime() - verifiedMs) / (24 * 60 * 60 * 1000));
|
|
34
|
+
stale.push({
|
|
35
|
+
id: fact.id,
|
|
36
|
+
path: fact.path,
|
|
37
|
+
relPath: fact.relPath,
|
|
38
|
+
title: fact.title,
|
|
39
|
+
confidence: fact.confidence,
|
|
40
|
+
lastVerified: fact.lastVerified,
|
|
41
|
+
daysSinceVerified,
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
// Deterministic order: by daysSinceVerified desc (oldest first), id asc.
|
|
46
|
+
stale.sort((a, b) => {
|
|
47
|
+
if (a.daysSinceVerified !== b.daysSinceVerified) {
|
|
48
|
+
return b.daysSinceVerified - a.daysSinceVerified;
|
|
49
|
+
}
|
|
50
|
+
return a.id.localeCompare(b.id);
|
|
51
|
+
});
|
|
52
|
+
unverifiable.sort((a, b) => a.id.localeCompare(b.id));
|
|
53
|
+
return { stale, unverifiable };
|
|
54
|
+
}
|
|
55
|
+
/**
|
|
56
|
+
* Execute a fact's `verify_command` and update `last_verified` on success.
|
|
57
|
+
* Returns a typed result describing what happened.
|
|
58
|
+
*
|
|
59
|
+
* The verify command runs in a child shell (bash via `-c`). CWD resolution:
|
|
60
|
+
* 1. `cwdOverride` (test seam)
|
|
61
|
+
* 2. Fact's frontmatter `working_dir:` field, resolved relative to vaultRoot
|
|
62
|
+
* 3. `<vaultRoot>/facts/` default
|
|
63
|
+
*/
|
|
64
|
+
export async function runFactVerify(options) {
|
|
65
|
+
const { fact, vaultRoot, cwdOverride, now = new Date(), skipExec = false } = options;
|
|
66
|
+
// Read the fact file fresh — we need the full frontmatter (verify_command,
|
|
67
|
+
// working_dir) which isn't in the lightweight CiterIndex FactRef.
|
|
68
|
+
const factContent = await readFile(fact.path, 'utf-8');
|
|
69
|
+
const parsed = matter(factContent);
|
|
70
|
+
const verifyCommand = parsed.data.verify_command;
|
|
71
|
+
const workingDir = parsed.data.working_dir;
|
|
72
|
+
if (typeof verifyCommand !== 'string' || verifyCommand.trim().length === 0) {
|
|
73
|
+
return {
|
|
74
|
+
factId: fact.id,
|
|
75
|
+
executed: false,
|
|
76
|
+
exitCode: null,
|
|
77
|
+
stdout: '',
|
|
78
|
+
stderr: 'no verify_command defined',
|
|
79
|
+
updated: false,
|
|
80
|
+
newLastVerified: undefined,
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
const cwd = cwdOverride ??
|
|
84
|
+
(typeof workingDir === 'string'
|
|
85
|
+
? resolve(vaultRoot, workingDir)
|
|
86
|
+
: resolve(vaultRoot, 'facts'));
|
|
87
|
+
if (skipExec) {
|
|
88
|
+
return finalize({
|
|
89
|
+
success: true,
|
|
90
|
+
exitCode: 0,
|
|
91
|
+
stdout: '[skipExec=true]',
|
|
92
|
+
stderr: '',
|
|
93
|
+
});
|
|
94
|
+
}
|
|
95
|
+
const result = await execShell(verifyCommand, cwd);
|
|
96
|
+
return finalize(result);
|
|
97
|
+
async function finalize(r) {
|
|
98
|
+
if (!r.success) {
|
|
99
|
+
return {
|
|
100
|
+
factId: fact.id,
|
|
101
|
+
executed: true,
|
|
102
|
+
exitCode: r.exitCode,
|
|
103
|
+
stdout: r.stdout,
|
|
104
|
+
stderr: r.stderr,
|
|
105
|
+
updated: false,
|
|
106
|
+
newLastVerified: undefined,
|
|
107
|
+
};
|
|
108
|
+
}
|
|
109
|
+
const newDate = now.toISOString().slice(0, 10);
|
|
110
|
+
parsed.data.last_verified = newDate;
|
|
111
|
+
const rewritten = matter.stringify(parsed.content, parsed.data);
|
|
112
|
+
await writeFile(fact.path, rewritten, 'utf-8');
|
|
113
|
+
return {
|
|
114
|
+
factId: fact.id,
|
|
115
|
+
executed: true,
|
|
116
|
+
exitCode: r.exitCode,
|
|
117
|
+
stdout: r.stdout,
|
|
118
|
+
stderr: r.stderr,
|
|
119
|
+
updated: true,
|
|
120
|
+
newLastVerified: newDate,
|
|
121
|
+
};
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
function execShell(command, cwd) {
|
|
125
|
+
return new Promise((resolvePromise) => {
|
|
126
|
+
if (!existsSync(cwd)) {
|
|
127
|
+
resolvePromise({
|
|
128
|
+
success: false,
|
|
129
|
+
exitCode: -1,
|
|
130
|
+
stdout: '',
|
|
131
|
+
stderr: `working dir does not exist: ${cwd}`,
|
|
132
|
+
});
|
|
133
|
+
return;
|
|
134
|
+
}
|
|
135
|
+
const child = spawn('bash', ['-c', command], { cwd });
|
|
136
|
+
let stdout = '';
|
|
137
|
+
let stderr = '';
|
|
138
|
+
child.stdout.on('data', (chunk) => (stdout += chunk.toString()));
|
|
139
|
+
child.stderr.on('data', (chunk) => (stderr += chunk.toString()));
|
|
140
|
+
child.on('close', (code) => {
|
|
141
|
+
resolvePromise({
|
|
142
|
+
success: code === 0,
|
|
143
|
+
exitCode: code ?? -1,
|
|
144
|
+
stdout,
|
|
145
|
+
stderr,
|
|
146
|
+
});
|
|
147
|
+
});
|
|
148
|
+
child.on('error', (err) => {
|
|
149
|
+
resolvePromise({
|
|
150
|
+
success: false,
|
|
151
|
+
exitCode: -1,
|
|
152
|
+
stdout: '',
|
|
153
|
+
stderr: err.message,
|
|
154
|
+
});
|
|
155
|
+
});
|
|
156
|
+
});
|
|
157
|
+
}
|
|
158
|
+
//# sourceMappingURL=audit.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"audit.js","sourceRoot":"","sources":["../../../src/core/knowledge-base/audit.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Frontmatter mutation for `hewtd cite` (2.3.0 PR3).
|
|
3
|
+
*
|
|
4
|
+
* Inserts a `cites:` entry into the nearest `symptoms:` block in a playbook,
|
|
5
|
+
* or creates a new top-level `symptoms:` block if one doesn't exist.
|
|
6
|
+
* Idempotent: re-citing the same fact in the same symptom entry is a no-op.
|
|
7
|
+
*
|
|
8
|
+
* Round-trip safety: uses gray-matter to preserve body content. Frontmatter
|
|
9
|
+
* key order is preserved for keys that already existed; new keys (symptoms)
|
|
10
|
+
* append at the end.
|
|
11
|
+
*/
|
|
12
|
+
export interface CiteOptions {
|
|
13
|
+
/** Absolute path to the playbook file. */
|
|
14
|
+
playbookPath: string;
|
|
15
|
+
/** Fact id to insert into the symptoms block. */
|
|
16
|
+
factId: string;
|
|
17
|
+
/**
|
|
18
|
+
* Optional symptom identifier — if present, adds the citation to the
|
|
19
|
+
* matching entry. If absent, adds to the FIRST symptoms entry (or creates
|
|
20
|
+
* a single placeholder symptom).
|
|
21
|
+
*/
|
|
22
|
+
symptomMatch?: {
|
|
23
|
+
alert_name?: string;
|
|
24
|
+
user_phrase?: string;
|
|
25
|
+
error_pattern?: string;
|
|
26
|
+
};
|
|
27
|
+
/** If true, returns the proposed content without writing the file. */
|
|
28
|
+
dryRun?: boolean;
|
|
29
|
+
}
|
|
30
|
+
export interface CiteResult {
|
|
31
|
+
playbookPath: string;
|
|
32
|
+
factId: string;
|
|
33
|
+
/** What we did: inserted, already_present (no-op), or created_block. */
|
|
34
|
+
action: 'inserted' | 'already_present' | 'created_block';
|
|
35
|
+
/** Index of the symptoms entry the citation was added to. */
|
|
36
|
+
symptomIndex: number;
|
|
37
|
+
/** The full new file content. */
|
|
38
|
+
newContent: string;
|
|
39
|
+
}
|
|
40
|
+
export declare function cite(options: CiteOptions): Promise<CiteResult>;
|
|
41
|
+
//# sourceMappingURL=cite.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cite.d.ts","sourceRoot":"","sources":["../../../src/core/knowledge-base/cite.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAKH,MAAM,WAAW,WAAW;IAC1B,0CAA0C;IAC1C,YAAY,EAAE,MAAM,CAAC;IACrB,iDAAiD;IACjD,MAAM,EAAE,MAAM,CAAC;IACf;;;;OAIG;IACH,YAAY,CAAC,EAAE;QACb,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,aAAa,CAAC,EAAE,MAAM,CAAC;KACxB,CAAC;IACF,sEAAsE;IACtE,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,WAAW,UAAU;IACzB,YAAY,EAAE,MAAM,CAAC;IACrB,MAAM,EAAE,MAAM,CAAC;IACf,wEAAwE;IACxE,MAAM,EAAE,UAAU,GAAG,iBAAiB,GAAG,eAAe,CAAC;IACzD,6DAA6D;IAC7D,YAAY,EAAE,MAAM,CAAC;IACrB,iCAAiC;IACjC,UAAU,EAAE,MAAM,CAAC;CACpB;AAWD,wBAAsB,IAAI,CAAC,OAAO,EAAE,WAAW,GAAG,OAAO,CAAC,UAAU,CAAC,CA2DpE"}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Frontmatter mutation for `hewtd cite` (2.3.0 PR3).
|
|
3
|
+
*
|
|
4
|
+
* Inserts a `cites:` entry into the nearest `symptoms:` block in a playbook,
|
|
5
|
+
* or creates a new top-level `symptoms:` block if one doesn't exist.
|
|
6
|
+
* Idempotent: re-citing the same fact in the same symptom entry is a no-op.
|
|
7
|
+
*
|
|
8
|
+
* Round-trip safety: uses gray-matter to preserve body content. Frontmatter
|
|
9
|
+
* key order is preserved for keys that already existed; new keys (symptoms)
|
|
10
|
+
* append at the end.
|
|
11
|
+
*/
|
|
12
|
+
import { readFile, writeFile } from 'fs/promises';
|
|
13
|
+
import matter from 'gray-matter';
|
|
14
|
+
export async function cite(options) {
|
|
15
|
+
const { playbookPath, factId, symptomMatch, dryRun = false } = options;
|
|
16
|
+
const content = await readFile(playbookPath, 'utf-8');
|
|
17
|
+
const parsed = matter(content);
|
|
18
|
+
const data = (parsed.data ?? {});
|
|
19
|
+
const symptoms = Array.isArray(data.symptoms)
|
|
20
|
+
? data.symptoms
|
|
21
|
+
: [];
|
|
22
|
+
let action;
|
|
23
|
+
let symptomIndex;
|
|
24
|
+
if (symptoms.length === 0) {
|
|
25
|
+
// No symptoms block — create one with a single placeholder entry.
|
|
26
|
+
symptoms.push({
|
|
27
|
+
alert_name: '<TODO: specify alert_name, user_phrase, or error_pattern>',
|
|
28
|
+
target: '<TODO: anchor>',
|
|
29
|
+
cites: [factId],
|
|
30
|
+
});
|
|
31
|
+
symptomIndex = 0;
|
|
32
|
+
action = 'created_block';
|
|
33
|
+
}
|
|
34
|
+
else {
|
|
35
|
+
// Find the target entry. If symptomMatch is provided, look for a match;
|
|
36
|
+
// otherwise default to the first entry.
|
|
37
|
+
let targetIdx = 0;
|
|
38
|
+
if (symptomMatch) {
|
|
39
|
+
const matched = symptoms.findIndex((s) => matchesSymptom(s, symptomMatch));
|
|
40
|
+
if (matched >= 0)
|
|
41
|
+
targetIdx = matched;
|
|
42
|
+
}
|
|
43
|
+
const entry = symptoms[targetIdx];
|
|
44
|
+
const cites = Array.isArray(entry.cites) ? entry.cites : [];
|
|
45
|
+
if (cites.includes(factId)) {
|
|
46
|
+
action = 'already_present';
|
|
47
|
+
}
|
|
48
|
+
else {
|
|
49
|
+
cites.push(factId);
|
|
50
|
+
entry.cites = cites;
|
|
51
|
+
action = 'inserted';
|
|
52
|
+
}
|
|
53
|
+
symptomIndex = targetIdx;
|
|
54
|
+
}
|
|
55
|
+
data.symptoms = symptoms;
|
|
56
|
+
const newContent = matter.stringify(parsed.content, data);
|
|
57
|
+
if (!dryRun && action !== 'already_present') {
|
|
58
|
+
await writeFile(playbookPath, newContent, 'utf-8');
|
|
59
|
+
}
|
|
60
|
+
return {
|
|
61
|
+
playbookPath,
|
|
62
|
+
factId,
|
|
63
|
+
action,
|
|
64
|
+
symptomIndex,
|
|
65
|
+
newContent,
|
|
66
|
+
};
|
|
67
|
+
}
|
|
68
|
+
function matchesSymptom(entry, match) {
|
|
69
|
+
if (match.alert_name && entry.alert_name === match.alert_name)
|
|
70
|
+
return true;
|
|
71
|
+
if (match.error_pattern && entry.error_pattern === match.error_pattern)
|
|
72
|
+
return true;
|
|
73
|
+
if (match.user_phrase) {
|
|
74
|
+
const ep = entry.user_phrase;
|
|
75
|
+
if (typeof ep === 'string' && ep === match.user_phrase)
|
|
76
|
+
return true;
|
|
77
|
+
if (Array.isArray(ep) && ep.includes(match.user_phrase))
|
|
78
|
+
return true;
|
|
79
|
+
}
|
|
80
|
+
return false;
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=cite.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cite.js","sourceRoot":"","sources":["../../../src/core/knowledge-base/cite.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Citation graph walker for knowledge-base primitives (2.3.0).
|
|
3
|
+
*
|
|
4
|
+
* Builds the per-fact citation index from three source kinds:
|
|
5
|
+
* - Facts (`<vault>/facts/<id>.md`) — the canonical fact corpus.
|
|
6
|
+
* - Incident-facts bridges (`<vault>/incidents/<slug>/facts.md`) — produced /
|
|
7
|
+
* strengthened / weakened edges.
|
|
8
|
+
* - Playbooks (any file with `symptoms: [...]` frontmatter) — `cites` edges
|
|
9
|
+
* from each symptom entry to the facts the playbook step depends on.
|
|
10
|
+
*
|
|
11
|
+
* Used by:
|
|
12
|
+
* - `facts/INDEX.md` generator (PR2) — to compute citer counts per fact.
|
|
13
|
+
* - `hewtd find-citers <fact-id>` CLI command (PR3) — typed structure output.
|
|
14
|
+
* - Dangling-citation linting (future PR) — flags `cites:` pointing at
|
|
15
|
+
* non-existent facts.
|
|
16
|
+
*/
|
|
17
|
+
export interface FactRef {
|
|
18
|
+
/** Fact id (from frontmatter `id:`). */
|
|
19
|
+
id: string;
|
|
20
|
+
/** Absolute path to the fact's markdown file. */
|
|
21
|
+
path: string;
|
|
22
|
+
/** Path relative to the project root (for stable, diff-friendly indexes). */
|
|
23
|
+
relPath: string;
|
|
24
|
+
/** Frontmatter title. */
|
|
25
|
+
title: string;
|
|
26
|
+
/** Confidence enum value, if present. */
|
|
27
|
+
confidence: string | undefined;
|
|
28
|
+
/** YYYY-MM-DD or null if missing/malformed. */
|
|
29
|
+
lastVerified: string | undefined;
|
|
30
|
+
/** Tags from frontmatter. */
|
|
31
|
+
tags: string[];
|
|
32
|
+
}
|
|
33
|
+
export interface IncidentRef {
|
|
34
|
+
/** Incident id (from narrative.md frontmatter `id:`). */
|
|
35
|
+
id: string;
|
|
36
|
+
/** Absolute path to the incident folder. */
|
|
37
|
+
folderPath: string;
|
|
38
|
+
/** Project-relative folder path. */
|
|
39
|
+
relFolderPath: string;
|
|
40
|
+
/** Frontmatter title from narrative.md. */
|
|
41
|
+
title: string;
|
|
42
|
+
/** YYYY-MM-DD. */
|
|
43
|
+
date: string | undefined;
|
|
44
|
+
severity: string | undefined;
|
|
45
|
+
resolution_status: string | undefined;
|
|
46
|
+
components: string[];
|
|
47
|
+
/** Fact ids produced by this incident (from facts.md). */
|
|
48
|
+
produced: string[];
|
|
49
|
+
strengthened: string[];
|
|
50
|
+
weakened: string[];
|
|
51
|
+
}
|
|
52
|
+
export interface PlaybookCitation {
|
|
53
|
+
/** Project-relative path to the playbook. */
|
|
54
|
+
relPath: string;
|
|
55
|
+
/** Absolute path. */
|
|
56
|
+
path: string;
|
|
57
|
+
/** Frontmatter title. */
|
|
58
|
+
title: string;
|
|
59
|
+
/** Anchor within the playbook (e.g. `#vault-down-auth-staging`). */
|
|
60
|
+
target: string;
|
|
61
|
+
/** Symptom kind that triggered the citation. */
|
|
62
|
+
kind: 'alert_name' | 'user_phrase' | 'error_pattern';
|
|
63
|
+
/** The matching key (string or array, depending on kind). */
|
|
64
|
+
key: string | string[];
|
|
65
|
+
severity: string | undefined;
|
|
66
|
+
}
|
|
67
|
+
export interface CiterIndex {
|
|
68
|
+
/** All discovered facts, keyed by id. */
|
|
69
|
+
facts: Map<string, FactRef>;
|
|
70
|
+
/** All discovered incident folders, keyed by id. */
|
|
71
|
+
incidents: Map<string, IncidentRef>;
|
|
72
|
+
/**
|
|
73
|
+
* Citation edges per fact id. A fact id appearing here may not have a
|
|
74
|
+
* matching entry in `facts` — that's a dangling citation, detected by
|
|
75
|
+
* the caller.
|
|
76
|
+
*/
|
|
77
|
+
citers: Map<string, PlaybookCitation[]>;
|
|
78
|
+
}
|
|
79
|
+
/**
|
|
80
|
+
* Typed structure returned by `findCiters(factId)`. Matches the shape the
|
|
81
|
+
* `hewtd find-citers` CLI command will print and the structure documented
|
|
82
|
+
* in `docs/knowledge-base-primitives.md`.
|
|
83
|
+
*/
|
|
84
|
+
export interface FindCitersResult {
|
|
85
|
+
fact_id: string;
|
|
86
|
+
fact_exists: boolean;
|
|
87
|
+
citers: string[];
|
|
88
|
+
incidents_produced_in: string[];
|
|
89
|
+
incidents_strengthened_by: string[];
|
|
90
|
+
incidents_weakened_by: string[];
|
|
91
|
+
}
|
|
92
|
+
export interface BuildCiterIndexOptions {
|
|
93
|
+
/** Absolute path to the project root. */
|
|
94
|
+
projectRoot: string;
|
|
95
|
+
/** Absolute path to the vault root (default config: <root>/.documentation/knowledge-base/). */
|
|
96
|
+
vaultRoot: string;
|
|
97
|
+
/**
|
|
98
|
+
* Glob patterns (absolute, project-rooted) used to scan playbooks for
|
|
99
|
+
* `symptoms:` frontmatter blocks. The walker filters by frontmatter
|
|
100
|
+
* presence — files without a `symptoms:` block are skipped quickly.
|
|
101
|
+
*/
|
|
102
|
+
playbookGlobs: string[];
|
|
103
|
+
}
|
|
104
|
+
/**
|
|
105
|
+
* Walk the corpus and build a citer index. Designed to be cheap on no-vault
|
|
106
|
+
* trees: if the vault root doesn't exist, returns an empty index without
|
|
107
|
+
* scanning playbooks for symptoms (no point — no facts to cite).
|
|
108
|
+
*/
|
|
109
|
+
export declare function buildCiterIndex(options: BuildCiterIndexOptions): Promise<CiterIndex>;
|
|
110
|
+
/**
|
|
111
|
+
* Public lookup: typed structure for one fact id. Matches the shape the
|
|
112
|
+
* `hewtd find-citers` CLI command prints.
|
|
113
|
+
*/
|
|
114
|
+
export declare function findCitersInIndex(index: CiterIndex, factId: string): FindCitersResult;
|
|
115
|
+
/**
|
|
116
|
+
* Count distinct citers for a fact id. Used by the facts-index generator.
|
|
117
|
+
*/
|
|
118
|
+
export declare function citerCount(index: CiterIndex, factId: string): number;
|
|
119
|
+
//# sourceMappingURL=citers.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"citers.d.ts","sourceRoot":"","sources":["../../../src/core/knowledge-base/citers.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAOH,MAAM,WAAW,OAAO;IACtB,wCAAwC;IACxC,EAAE,EAAE,MAAM,CAAC;IACX,iDAAiD;IACjD,IAAI,EAAE,MAAM,CAAC;IACb,6EAA6E;IAC7E,OAAO,EAAE,MAAM,CAAC;IAChB,yBAAyB;IACzB,KAAK,EAAE,MAAM,CAAC;IACd,yCAAyC;IACzC,UAAU,EAAE,MAAM,GAAG,SAAS,CAAC;IAC/B,+CAA+C;IAC/C,YAAY,EAAE,MAAM,GAAG,SAAS,CAAC;IACjC,6BAA6B;IAC7B,IAAI,EAAE,MAAM,EAAE,CAAC;CAChB;AAED,MAAM,WAAW,WAAW;IAC1B,yDAAyD;IACzD,EAAE,EAAE,MAAM,CAAC;IACX,4CAA4C;IAC5C,UAAU,EAAE,MAAM,CAAC;IACnB,oCAAoC;IACpC,aAAa,EAAE,MAAM,CAAC;IACtB,2CAA2C;IAC3C,KAAK,EAAE,MAAM,CAAC;IACd,kBAAkB;IAClB,IAAI,EAAE,MAAM,GAAG,SAAS,CAAC;IACzB,QAAQ,EAAE,MAAM,GAAG,SAAS,CAAC;IAC7B,iBAAiB,EAAE,MAAM,GAAG,SAAS,CAAC;IACtC,UAAU,EAAE,MAAM,EAAE,CAAC;IACrB,0DAA0D;IAC1D,QAAQ,EAAE,MAAM,EAAE,CAAC;IACnB,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAED,MAAM,WAAW,gBAAgB;IAC/B,6CAA6C;IAC7C,OAAO,EAAE,MAAM,CAAC;IAChB,qBAAqB;IACrB,IAAI,EAAE,MAAM,CAAC;IACb,yBAAyB;IACzB,KAAK,EAAE,MAAM,CAAC;IACd,oEAAoE;IACpE,MAAM,EAAE,MAAM,CAAC;IACf,gDAAgD;IAChD,IAAI,EAAE,YAAY,GAAG,aAAa,GAAG,eAAe,CAAC;IACrD,6DAA6D;IAC7D,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC;IACvB,QAAQ,EAAE,MAAM,GAAG,SAAS,CAAC;CAC9B;AAED,MAAM,WAAW,UAAU;IACzB,yCAAyC;IACzC,KAAK,EAAE,GAAG,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAC5B,oDAAoD;IACpD,SAAS,EAAE,GAAG,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;IACpC;;;;OAIG;IACH,MAAM,EAAE,GAAG,CAAC,MAAM,EAAE,gBAAgB,EAAE,CAAC,CAAC;CACzC;AAED;;;;GAIG;AACH,MAAM,WAAW,gBAAgB;IAC/B,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,EAAE,OAAO,CAAC;IACrB,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,qBAAqB,EAAE,MAAM,EAAE,CAAC;IAChC,yBAAyB,EAAE,MAAM,EAAE,CAAC;IACpC,qBAAqB,EAAE,MAAM,EAAE,CAAC;CACjC;AAED,MAAM,WAAW,sBAAsB;IACrC,yCAAyC;IACzC,WAAW,EAAE,MAAM,CAAC;IACpB,+FAA+F;IAC/F,SAAS,EAAE,MAAM,CAAC;IAClB;;;;OAIG;IACH,aAAa,EAAE,MAAM,EAAE,CAAC;CACzB;AAMD;;;;GAIG;AACH,wBAAsB,eAAe,CACnC,OAAO,EAAE,sBAAsB,GAC9B,OAAO,CAAC,UAAU,CAAC,CAuDrB;AAiJD;;;GAGG;AACH,wBAAgB,iBAAiB,CAC/B,KAAK,EAAE,UAAU,EACjB,MAAM,EAAE,MAAM,GACb,gBAAgB,CAyBlB;AAED;;GAEG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,UAAU,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,CAQpE"}
|