@mfittko/repo-wiki 0.2.1

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 (190) hide show
  1. package/.llmwiki/schema.md +107 -0
  2. package/AGENTS.md +42 -0
  3. package/CHANGELOG.md +91 -0
  4. package/LICENSE +21 -0
  5. package/README.md +254 -0
  6. package/dist/bin/repo-wiki.d.ts +2 -0
  7. package/dist/bin/repo-wiki.js +7 -0
  8. package/dist/bin/repo-wiki.js.map +1 -0
  9. package/dist/src/cli.d.ts +1 -0
  10. package/dist/src/cli.js +404 -0
  11. package/dist/src/cli.js.map +1 -0
  12. package/dist/src/compiler.d.ts +55 -0
  13. package/dist/src/compiler.js +2046 -0
  14. package/dist/src/compiler.js.map +1 -0
  15. package/dist/src/config.d.ts +63 -0
  16. package/dist/src/config.js +86 -0
  17. package/dist/src/config.js.map +1 -0
  18. package/dist/src/context-assembler.d.ts +68 -0
  19. package/dist/src/context-assembler.js +378 -0
  20. package/dist/src/context-assembler.js.map +1 -0
  21. package/dist/src/data-model-signals.d.ts +1 -0
  22. package/dist/src/data-model-signals.js +13 -0
  23. package/dist/src/data-model-signals.js.map +1 -0
  24. package/dist/src/docs-ingestor.d.ts +138 -0
  25. package/dist/src/docs-ingestor.js +844 -0
  26. package/dist/src/docs-ingestor.js.map +1 -0
  27. package/dist/src/docs-linter.d.ts +14 -0
  28. package/dist/src/docs-linter.js +164 -0
  29. package/dist/src/docs-linter.js.map +1 -0
  30. package/dist/src/docs-validation.d.ts +36 -0
  31. package/dist/src/docs-validation.js +297 -0
  32. package/dist/src/docs-validation.js.map +1 -0
  33. package/dist/src/extractors.d.ts +50 -0
  34. package/dist/src/extractors.js +2275 -0
  35. package/dist/src/extractors.js.map +1 -0
  36. package/dist/src/frontmatter.d.ts +46 -0
  37. package/dist/src/frontmatter.js +377 -0
  38. package/dist/src/frontmatter.js.map +1 -0
  39. package/dist/src/index.d.ts +26 -0
  40. package/dist/src/index.js +18 -0
  41. package/dist/src/index.js.map +1 -0
  42. package/dist/src/init.d.ts +12 -0
  43. package/dist/src/init.js +121 -0
  44. package/dist/src/init.js.map +1 -0
  45. package/dist/src/language.d.ts +2 -0
  46. package/dist/src/language.js +62 -0
  47. package/dist/src/language.js.map +1 -0
  48. package/dist/src/linter.d.ts +33 -0
  49. package/dist/src/linter.js +398 -0
  50. package/dist/src/linter.js.map +1 -0
  51. package/dist/src/llm-provider.d.ts +267 -0
  52. package/dist/src/llm-provider.js +474 -0
  53. package/dist/src/llm-provider.js.map +1 -0
  54. package/dist/src/page-ownership.d.ts +38 -0
  55. package/dist/src/page-ownership.js +96 -0
  56. package/dist/src/page-ownership.js.map +1 -0
  57. package/dist/src/planner.d.ts +55 -0
  58. package/dist/src/planner.js +422 -0
  59. package/dist/src/planner.js.map +1 -0
  60. package/dist/src/prompts.d.ts +103 -0
  61. package/dist/src/prompts.js +344 -0
  62. package/dist/src/prompts.js.map +1 -0
  63. package/dist/src/publisher.d.ts +68 -0
  64. package/dist/src/publisher.js +662 -0
  65. package/dist/src/publisher.js.map +1 -0
  66. package/dist/src/repository-analysis.d.ts +88 -0
  67. package/dist/src/repository-analysis.js +485 -0
  68. package/dist/src/repository-analysis.js.map +1 -0
  69. package/dist/src/scanner.d.ts +122 -0
  70. package/dist/src/scanner.js +309 -0
  71. package/dist/src/scanner.js.map +1 -0
  72. package/dist/src/search.d.ts +71 -0
  73. package/dist/src/search.js +410 -0
  74. package/dist/src/search.js.map +1 -0
  75. package/dist/src/secret-patterns.d.ts +3 -0
  76. package/dist/src/secret-patterns.js +14 -0
  77. package/dist/src/secret-patterns.js.map +1 -0
  78. package/dist/src/utils/args.d.ts +2 -0
  79. package/dist/src/utils/args.js +19 -0
  80. package/dist/src/utils/args.js.map +1 -0
  81. package/dist/src/utils/dotenv.d.ts +7 -0
  82. package/dist/src/utils/dotenv.js +73 -0
  83. package/dist/src/utils/dotenv.js.map +1 -0
  84. package/dist/src/utils/fs.d.ts +22 -0
  85. package/dist/src/utils/fs.js +83 -0
  86. package/dist/src/utils/fs.js.map +1 -0
  87. package/dist/src/utils/git.d.ts +13 -0
  88. package/dist/src/utils/git.js +39 -0
  89. package/dist/src/utils/git.js.map +1 -0
  90. package/dist/src/wiki-graph.d.ts +74 -0
  91. package/dist/src/wiki-graph.js +335 -0
  92. package/dist/src/wiki-graph.js.map +1 -0
  93. package/dist/src/wiki-patch.d.ts +152 -0
  94. package/dist/src/wiki-patch.js +489 -0
  95. package/dist/src/wiki-patch.js.map +1 -0
  96. package/dist/src/wiki-query.d.ts +63 -0
  97. package/dist/src/wiki-query.js +255 -0
  98. package/dist/src/wiki-query.js.map +1 -0
  99. package/dist/test/cli.test.d.ts +1 -0
  100. package/dist/test/cli.test.js +514 -0
  101. package/dist/test/cli.test.js.map +1 -0
  102. package/dist/test/compiler-eval.test.d.ts +1 -0
  103. package/dist/test/compiler-eval.test.js +234 -0
  104. package/dist/test/compiler-eval.test.js.map +1 -0
  105. package/dist/test/compiler.test.d.ts +1 -0
  106. package/dist/test/compiler.test.js +2537 -0
  107. package/dist/test/compiler.test.js.map +1 -0
  108. package/dist/test/context-assembler.test.d.ts +1 -0
  109. package/dist/test/context-assembler.test.js +379 -0
  110. package/dist/test/context-assembler.test.js.map +1 -0
  111. package/dist/test/docs-linter.test.d.ts +1 -0
  112. package/dist/test/docs-linter.test.js +900 -0
  113. package/dist/test/docs-linter.test.js.map +1 -0
  114. package/dist/test/dotenv.test.d.ts +1 -0
  115. package/dist/test/dotenv.test.js +77 -0
  116. package/dist/test/dotenv.test.js.map +1 -0
  117. package/dist/test/extractors-go.test.d.ts +1 -0
  118. package/dist/test/extractors-go.test.js +393 -0
  119. package/dist/test/extractors-go.test.js.map +1 -0
  120. package/dist/test/extractors-rust.test.d.ts +1 -0
  121. package/dist/test/extractors-rust.test.js +219 -0
  122. package/dist/test/extractors-rust.test.js.map +1 -0
  123. package/dist/test/extractors-utils.test.d.ts +1 -0
  124. package/dist/test/extractors-utils.test.js +786 -0
  125. package/dist/test/extractors-utils.test.js.map +1 -0
  126. package/dist/test/fixtures/compiler-e2e/basic-node-service/repo/infra/deploy.d.ts +1 -0
  127. package/dist/test/fixtures/compiler-e2e/basic-node-service/repo/infra/deploy.js +4 -0
  128. package/dist/test/fixtures/compiler-e2e/basic-node-service/repo/infra/deploy.js.map +1 -0
  129. package/dist/test/frontmatter.test.d.ts +1 -0
  130. package/dist/test/frontmatter.test.js +287 -0
  131. package/dist/test/frontmatter.test.js.map +1 -0
  132. package/dist/test/init-planner.test.d.ts +1 -0
  133. package/dist/test/init-planner.test.js +688 -0
  134. package/dist/test/init-planner.test.js.map +1 -0
  135. package/dist/test/linter.test.d.ts +1 -0
  136. package/dist/test/linter.test.js +426 -0
  137. package/dist/test/linter.test.js.map +1 -0
  138. package/dist/test/llm-provider.test.d.ts +1 -0
  139. package/dist/test/llm-provider.test.js +783 -0
  140. package/dist/test/llm-provider.test.js.map +1 -0
  141. package/dist/test/page-ownership.test.d.ts +1 -0
  142. package/dist/test/page-ownership.test.js +247 -0
  143. package/dist/test/page-ownership.test.js.map +1 -0
  144. package/dist/test/publisher.test.d.ts +1 -0
  145. package/dist/test/publisher.test.js +1297 -0
  146. package/dist/test/publisher.test.js.map +1 -0
  147. package/dist/test/repository-analysis.test.d.ts +1 -0
  148. package/dist/test/repository-analysis.test.js +182 -0
  149. package/dist/test/repository-analysis.test.js.map +1 -0
  150. package/dist/test/run-compiled-tests.d.ts +1 -0
  151. package/dist/test/run-compiled-tests.js +48 -0
  152. package/dist/test/run-compiled-tests.js.map +1 -0
  153. package/dist/test/scanner.test.d.ts +1 -0
  154. package/dist/test/scanner.test.js +551 -0
  155. package/dist/test/scanner.test.js.map +1 -0
  156. package/dist/test/search.test.d.ts +1 -0
  157. package/dist/test/search.test.js +92 -0
  158. package/dist/test/search.test.js.map +1 -0
  159. package/dist/test/update-changelog.test.d.ts +1 -0
  160. package/dist/test/update-changelog.test.js +125 -0
  161. package/dist/test/update-changelog.test.js.map +1 -0
  162. package/dist/test/wiki-graph.test.d.ts +1 -0
  163. package/dist/test/wiki-graph.test.js +164 -0
  164. package/dist/test/wiki-graph.test.js.map +1 -0
  165. package/dist/test/wiki-patch.test.d.ts +1 -0
  166. package/dist/test/wiki-patch.test.js +610 -0
  167. package/dist/test/wiki-patch.test.js.map +1 -0
  168. package/dist/test/wiki-query.test.d.ts +1 -0
  169. package/dist/test/wiki-query.test.js +163 -0
  170. package/dist/test/wiki-query.test.js.map +1 -0
  171. package/docs/PLAN.md +993 -0
  172. package/docs/WHY.md +61 -0
  173. package/docs/plans/agent-integration.md +85 -0
  174. package/docs/plans/ci-publishing.md +111 -0
  175. package/docs/plans/doc-validation.md +92 -0
  176. package/docs/plans/github-action.md +113 -0
  177. package/docs/plans/incremental-mode.md +98 -0
  178. package/docs/plans/karpathy-llm-wiki-alignment.md +84 -0
  179. package/docs/plans/llm-compiler.md +160 -0
  180. package/docs/plans/production-scanner.md +104 -0
  181. package/docs/plans/query-and-file-back.md +103 -0
  182. package/docs/plans/search-index.md +118 -0
  183. package/docs/plans/trust-hardening.md +74 -0
  184. package/docs/plans/wiki-graph.md +183 -0
  185. package/docs/plans/wiki-health.md +76 -0
  186. package/package.json +83 -0
  187. package/prompts/compiler.md +16 -0
  188. package/prompts/lint.md +18 -0
  189. package/prompts/page-templates.md +25 -0
  190. package/skills/repo-wiki-cli/SKILL.md +139 -0
@@ -0,0 +1,152 @@
1
+ /**
2
+ * Structured wiki patch parsing and lint-gated acceptance.
3
+ *
4
+ * LLM output is treated as untrusted and must be parsed, validated, and
5
+ * accepted only after lint gates pass. Free-form markdown cannot bypass
6
+ * patch validation; invalid patches produce actionable errors and do not
7
+ * overwrite existing wiki pages.
8
+ *
9
+ * Typical usage:
10
+ *
11
+ * // Parse and validate (throws WikiPatchError on error-level failures):
12
+ * const patch = parseWikiPatch(llmOutput, 'Module-Auth');
13
+ *
14
+ * // Inspect issues without throwing:
15
+ * const issues = validateWikiPatch(llmOutput, 'Module-Auth');
16
+ *
17
+ * // Full synthesis pipeline with retry:
18
+ * const patch = await synthesizeWikiPage(provider, request, { maxRetries: 2 });
19
+ */
20
+ import type { LLMProvider, LLMRequest } from './llm-provider.js';
21
+ /** A single lint issue found during patch validation. */
22
+ export interface WikiPatchIssue {
23
+ /** Severity of the issue. Error-level issues block acceptance; warnings are informational. */
24
+ level: 'error' | 'warning';
25
+ /** Machine-readable issue code. */
26
+ code: string;
27
+ /** Human-readable description of the problem. */
28
+ message: string;
29
+ }
30
+ /** Required and optional frontmatter fields recognized in wiki patches. */
31
+ export interface WikiPatchFrontmatter {
32
+ /** Git commit SHA that was current when this page was compiled. */
33
+ source_commit: string;
34
+ /** Page archetype identifier (e.g. "module", "home", "architecture"). */
35
+ kind: string;
36
+ /** Repository source paths cited by this page. */
37
+ source_paths: string[];
38
+ /** ISO-8601 timestamp of compilation. */
39
+ compiled_at: string;
40
+ /** Page ownership state emitted by the compiler. */
41
+ page_state?: string;
42
+ /** Remote URL or shorthand of the source repository. */
43
+ source_repo?: string;
44
+ /** Additional frontmatter fields passed through from the LLM. */
45
+ [key: string]: unknown;
46
+ }
47
+ /**
48
+ * Structured representation of a validated LLM-generated wiki page.
49
+ *
50
+ * A `WikiPatch` is produced only when all error-level lint gates pass. It
51
+ * carries the parsed frontmatter, the markdown body, and the full normalized
52
+ * content so that callers can apply human-notes preservation and write the
53
+ * final page without re-parsing.
54
+ */
55
+ export interface WikiPatch {
56
+ /** Wiki page slug/filename without `.md` (e.g. `"Module-Auth"`). */
57
+ pageName: string;
58
+ /** Full, normalized markdown content (frontmatter + body). */
59
+ content: string;
60
+ /** Parsed frontmatter fields extracted from the content. */
61
+ frontmatter: WikiPatchFrontmatter;
62
+ /** Markdown body — everything after the closing `---` of the frontmatter. */
63
+ body: string;
64
+ }
65
+ /**
66
+ * Thrown by `parseWikiPatch` when one or more error-level lint gates fail.
67
+ *
68
+ * The `issues` array contains all problems found (both errors and warnings),
69
+ * giving callers enough information to log actionable diagnostics or feed
70
+ * failure details back to the LLM on retry.
71
+ *
72
+ * Example:
73
+ * try {
74
+ * const patch = parseWikiPatch(llmOutput, 'Module-Auth');
75
+ * } catch (err) {
76
+ * if (err instanceof WikiPatchError) {
77
+ * for (const issue of err.issues) console.error(issue.message);
78
+ * }
79
+ * }
80
+ */
81
+ export declare class WikiPatchError extends Error {
82
+ /** Wiki page slug this error pertains to. */
83
+ readonly pageName: string;
84
+ /** Full list of validation issues (errors and warnings). */
85
+ readonly issues: WikiPatchIssue[];
86
+ constructor(message: string, pageName: string, issues: WikiPatchIssue[]);
87
+ }
88
+ /** Options for the synthesis pipeline (`synthesizeWikiPage`). */
89
+ export interface SynthesizeOptions {
90
+ /**
91
+ * Maximum number of additional synthesis attempts when the first response
92
+ * fails validation. Defaults to 0 (no retries).
93
+ */
94
+ maxRetries?: number;
95
+ }
96
+ /**
97
+ * Validate raw LLM-generated content as a structured wiki patch.
98
+ *
99
+ * Returns the full list of issues found (errors and warnings). This is the
100
+ * non-throwing variant; call `parseWikiPatch` to get a validated `WikiPatch`
101
+ * or a thrown `WikiPatchError`.
102
+ *
103
+ * Lint gates applied (error-level):
104
+ * 1. `empty-content` – LLM returned empty or whitespace-only content.
105
+ * 2. `missing-frontmatter` – Content does not begin with a `---` YAML block.
106
+ * 3. `missing-source-commit` – Frontmatter lacks a `source_commit` field.
107
+ * 4. `missing-kind` – Frontmatter lacks a `kind` field.
108
+ * 5. `missing-compiled-at` – Frontmatter lacks a `compiled_at` field.
109
+ * 6. `empty-body` – No markdown content after the frontmatter block.
110
+ * 7. `secret-like-content` – Content matches a known credential pattern.
111
+ * 8. `invalid-source-paths` – `source_paths` contains non-string or blank entries.
112
+ *
113
+ * Lint gates applied (warning-level):
114
+ * 9. `missing-source-paths` – Frontmatter lacks a `source_paths` array.
115
+ */
116
+ export declare function validateWikiPatch(rawContent: string, pageName: string): WikiPatchIssue[];
117
+ /**
118
+ * Parse and validate LLM-generated content as a structured wiki patch.
119
+ *
120
+ * Throws `WikiPatchError` if any error-level lint gate fails. Callers should
121
+ * catch this error to log actionable diagnostics, optionally feed failure
122
+ * details back into the next LLM request, or skip the page.
123
+ *
124
+ * Warnings are attached to the thrown error's `issues` array (when it throws)
125
+ * or are silently surfaced (when the patch is valid). If callers need to
126
+ * inspect warnings on a successful parse, use `validateWikiPatch` instead.
127
+ *
128
+ * @param rawContent - Raw LLM output string to validate.
129
+ * @param pageName - Wiki page slug (e.g. `"Module-Auth"`) used in messages.
130
+ * @returns A validated `WikiPatch` ready for human-notes injection and writing.
131
+ * @throws {WikiPatchError} When one or more error-level issues are found.
132
+ */
133
+ export declare function parseWikiPatch(rawContent: string, pageName: string): WikiPatch;
134
+ /**
135
+ * Call an LLM provider and return the response as a validated `WikiPatch`.
136
+ *
137
+ * Validation runs after every provider response. If a response fails
138
+ * validation and `maxRetries > 0`, the provider is called again. The last
139
+ * thrown `WikiPatchError` is re-thrown when all attempts are exhausted.
140
+ *
141
+ * This makes it impossible for free-form LLM output to bypass patch
142
+ * validation and overwrite wiki pages.
143
+ *
144
+ * @param provider - LLM provider (mock or hosted).
145
+ * @param request - Pre-built `LLMRequest` (use `buildRequest` to assemble).
146
+ * @param options - Optional `{ maxRetries }` (default 0).
147
+ * @returns A validated `WikiPatch`.
148
+ * @throws {WikiPatchError} When all synthesis attempts produce invalid patches.
149
+ * @throws {LLMProviderError} On unrecoverable provider failures.
150
+ * @throws {RangeError} When `maxRetries` is not a non-negative finite number.
151
+ */
152
+ export declare function synthesizeWikiPage(provider: LLMProvider, request: LLMRequest, options?: SynthesizeOptions): Promise<WikiPatch>;
@@ -0,0 +1,489 @@
1
+ /**
2
+ * Structured wiki patch parsing and lint-gated acceptance.
3
+ *
4
+ * LLM output is treated as untrusted and must be parsed, validated, and
5
+ * accepted only after lint gates pass. Free-form markdown cannot bypass
6
+ * patch validation; invalid patches produce actionable errors and do not
7
+ * overwrite existing wiki pages.
8
+ *
9
+ * Typical usage:
10
+ *
11
+ * // Parse and validate (throws WikiPatchError on error-level failures):
12
+ * const patch = parseWikiPatch(llmOutput, 'Module-Auth');
13
+ *
14
+ * // Inspect issues without throwing:
15
+ * const issues = validateWikiPatch(llmOutput, 'Module-Auth');
16
+ *
17
+ * // Full synthesis pipeline with retry:
18
+ * const patch = await synthesizeWikiPage(provider, request, { maxRetries: 2 });
19
+ */
20
+ import { containsSecretLikeContent } from './secret-patterns.js';
21
+ // ── Structured error ───────────────────────────────────────────────────────
22
+ /**
23
+ * Thrown by `parseWikiPatch` when one or more error-level lint gates fail.
24
+ *
25
+ * The `issues` array contains all problems found (both errors and warnings),
26
+ * giving callers enough information to log actionable diagnostics or feed
27
+ * failure details back to the LLM on retry.
28
+ *
29
+ * Example:
30
+ * try {
31
+ * const patch = parseWikiPatch(llmOutput, 'Module-Auth');
32
+ * } catch (err) {
33
+ * if (err instanceof WikiPatchError) {
34
+ * for (const issue of err.issues) console.error(issue.message);
35
+ * }
36
+ * }
37
+ */
38
+ export class WikiPatchError extends Error {
39
+ /** Wiki page slug this error pertains to. */
40
+ pageName;
41
+ /** Full list of validation issues (errors and warnings). */
42
+ issues;
43
+ constructor(message, pageName, issues) {
44
+ super(message);
45
+ this.name = 'WikiPatchError';
46
+ this.pageName = pageName;
47
+ this.issues = issues;
48
+ }
49
+ }
50
+ // ── Frontmatter parsing ────────────────────────────────────────────────────
51
+ /**
52
+ * Split a markdown document into its frontmatter block and body.
53
+ *
54
+ * Returns `{ frontmatterRaw: null, body: content }` when the document does
55
+ * not begin with a valid `---`-delimited YAML block.
56
+ */
57
+ function stripSurroundingMarkdownFence(content) {
58
+ const normalized = content.replace(/^\uFEFF/, '').replace(/\r\n/g, '\n');
59
+ const trimmed = normalized.trim();
60
+ const fence = /^```[A-Za-z0-9_-]*[ \t]*\n([\s\S]*?)\n?```[ \t]*$/.exec(trimmed);
61
+ if (!fence) {
62
+ return normalized;
63
+ }
64
+ const inner = fence[1].replace(/^\uFEFF/, '').replace(/\r\n/g, '\n');
65
+ return inner.startsWith('---\n') ? inner : normalized;
66
+ }
67
+ function normalizeLLMOutput(content) {
68
+ return stripSurroundingMarkdownFence(content).replace(/^\uFEFF/, '').replace(/\r\n/g, '\n');
69
+ }
70
+ function splitFrontmatterAndBody(content) {
71
+ const normalized = normalizeLLMOutput(content);
72
+ const opening = normalized.match(/^---[ \t]*\n/);
73
+ if (!opening) {
74
+ return { frontmatterRaw: null, body: normalized };
75
+ }
76
+ const closingPattern = /^---[ \t]*$/gm;
77
+ closingPattern.lastIndex = opening[0].length;
78
+ const closing = closingPattern.exec(normalized);
79
+ if (!closing) {
80
+ return { frontmatterRaw: null, body: normalized };
81
+ }
82
+ const frontmatterRaw = normalized.slice(opening[0].length, closing.index);
83
+ // Strip the single newline that separates frontmatter from the body.
84
+ const body = normalized.slice(closing.index + closing[0].length).replace(/^\n/, '');
85
+ return { frontmatterRaw, body };
86
+ }
87
+ /**
88
+ * Parse a raw YAML frontmatter string into a key→value record.
89
+ *
90
+ * Handles the frontmatter subset repo-wiki emits and asks LLMs to return:
91
+ * top-level `key: value` pairs, JSON-quoted or bare scalar values, JSON-style
92
+ * inline arrays, and indented block sequences. It intentionally does not try
93
+ * to be a general YAML parser.
94
+ */
95
+ function parseFrontmatterFields(raw) {
96
+ const fields = {};
97
+ const lines = raw.split('\n');
98
+ let i = 0;
99
+ while (i < lines.length) {
100
+ const line = lines[i];
101
+ const colonIdx = line.indexOf(':');
102
+ if (colonIdx === -1) {
103
+ i++;
104
+ continue;
105
+ }
106
+ const key = line.slice(0, colonIdx).trim();
107
+ if (!key || key.startsWith('#')) {
108
+ i++;
109
+ continue;
110
+ }
111
+ const rawValue = line.slice(colonIdx + 1).trim();
112
+ if (rawValue === '[]') {
113
+ // Inline empty array
114
+ fields[key] = [];
115
+ i++;
116
+ continue;
117
+ }
118
+ if (rawValue === '') {
119
+ // Possible block sequence: collect lines that start with " -"
120
+ const items = [];
121
+ i++;
122
+ while (i < lines.length && /^\s+-/.test(lines[i])) {
123
+ const item = lines[i].replace(/^\s*-\s*/, '').trim();
124
+ items.push(parseScalar(item));
125
+ i++;
126
+ }
127
+ fields[key] = items;
128
+ continue;
129
+ }
130
+ // Inline array: `key: ["a", "b"]`
131
+ if (rawValue.startsWith('[') && rawValue.endsWith(']')) {
132
+ try {
133
+ const parsed = JSON.parse(rawValue);
134
+ if (Array.isArray(parsed)) {
135
+ fields[key] = parsed;
136
+ i++;
137
+ continue;
138
+ }
139
+ }
140
+ catch {
141
+ // Fall through to scalar parsing
142
+ }
143
+ }
144
+ fields[key] = parseScalar(rawValue);
145
+ i++;
146
+ }
147
+ return fields;
148
+ }
149
+ /**
150
+ * Parse a scalar YAML or JSON value into its native type.
151
+ *
152
+ * Handles JSON-quoted strings, booleans, null, numbers, and bare YAML strings.
153
+ */
154
+ function parseScalar(value) {
155
+ if (!value)
156
+ return '';
157
+ // Try JSON.parse for quoted strings, numbers, booleans, null
158
+ try {
159
+ const parsed = JSON.parse(value);
160
+ if (typeof parsed === 'string' || typeof parsed === 'number' || typeof parsed === 'boolean' || parsed === null)
161
+ return parsed;
162
+ }
163
+ catch {
164
+ // Fall through
165
+ }
166
+ return value;
167
+ }
168
+ // ── Validation ─────────────────────────────────────────────────────────────
169
+ /**
170
+ * Validate raw LLM-generated content as a structured wiki patch.
171
+ *
172
+ * Returns the full list of issues found (errors and warnings). This is the
173
+ * non-throwing variant; call `parseWikiPatch` to get a validated `WikiPatch`
174
+ * or a thrown `WikiPatchError`.
175
+ *
176
+ * Lint gates applied (error-level):
177
+ * 1. `empty-content` – LLM returned empty or whitespace-only content.
178
+ * 2. `missing-frontmatter` – Content does not begin with a `---` YAML block.
179
+ * 3. `missing-source-commit` – Frontmatter lacks a `source_commit` field.
180
+ * 4. `missing-kind` – Frontmatter lacks a `kind` field.
181
+ * 5. `missing-compiled-at` – Frontmatter lacks a `compiled_at` field.
182
+ * 6. `empty-body` – No markdown content after the frontmatter block.
183
+ * 7. `secret-like-content` – Content matches a known credential pattern.
184
+ * 8. `invalid-source-paths` – `source_paths` contains non-string or blank entries.
185
+ *
186
+ * Lint gates applied (warning-level):
187
+ * 9. `missing-source-paths` – Frontmatter lacks a `source_paths` array.
188
+ */
189
+ export function validateWikiPatch(rawContent, pageName) {
190
+ const issues = [];
191
+ // 1. Non-empty content
192
+ if (!rawContent || !rawContent.trim()) {
193
+ issues.push({
194
+ level: 'error',
195
+ code: 'empty-content',
196
+ message: `${pageName}: LLM returned empty content.`,
197
+ });
198
+ return issues; // Further checks are meaningless without content
199
+ }
200
+ // 2. Valid frontmatter block
201
+ const normalizedContent = normalizeLLMOutput(rawContent);
202
+ const { frontmatterRaw, body } = splitFrontmatterAndBody(normalizedContent);
203
+ if (frontmatterRaw === null) {
204
+ issues.push({
205
+ level: 'error',
206
+ code: 'missing-frontmatter',
207
+ message: `${pageName}: content does not start with a valid YAML frontmatter block (---).`,
208
+ });
209
+ }
210
+ else {
211
+ const fields = parseFrontmatterFields(frontmatterRaw);
212
+ // 3. Required field: source_commit
213
+ const sourceCommit = fields['source_commit'];
214
+ if (!sourceCommit || typeof sourceCommit !== 'string' || !sourceCommit.trim()) {
215
+ issues.push({
216
+ level: 'error',
217
+ code: 'missing-source-commit',
218
+ message: `${pageName}: frontmatter is missing required field "source_commit".`,
219
+ });
220
+ }
221
+ // 4. Required field: kind
222
+ const kind = fields['kind'];
223
+ if (!kind || typeof kind !== 'string' || !kind.trim()) {
224
+ issues.push({
225
+ level: 'error',
226
+ code: 'missing-kind',
227
+ message: `${pageName}: frontmatter is missing required field "kind".`,
228
+ });
229
+ }
230
+ // 5. Required field: compiled_at
231
+ const compiledAt = fields['compiled_at'];
232
+ if (!compiledAt || typeof compiledAt !== 'string' || !compiledAt.trim()) {
233
+ issues.push({
234
+ level: 'error',
235
+ code: 'missing-compiled-at',
236
+ message: `${pageName}: frontmatter is missing required field "compiled_at".`,
237
+ });
238
+ }
239
+ // 6. Body must not be empty
240
+ if (!body || !body.trim()) {
241
+ issues.push({
242
+ level: 'error',
243
+ code: 'empty-body',
244
+ message: `${pageName}: patch contains a frontmatter block but no markdown body.`,
245
+ });
246
+ }
247
+ // 8/9. source_paths must be an array when present; a missing array is a warning.
248
+ const sourcePaths = fields['source_paths'];
249
+ if (sourcePaths === undefined) {
250
+ issues.push({
251
+ level: 'warning',
252
+ code: 'missing-source-paths',
253
+ message: `${pageName}: frontmatter is missing a "source_paths" array.`,
254
+ });
255
+ }
256
+ else if (!Array.isArray(sourcePaths)) {
257
+ issues.push({
258
+ level: 'error',
259
+ code: 'invalid-source-paths',
260
+ message: `${pageName}: frontmatter field "source_paths" must be an array when present.`,
261
+ });
262
+ }
263
+ else if (!sourcePaths.every(isNonEmptyString)) {
264
+ issues.push({
265
+ level: 'error',
266
+ code: 'invalid-source-paths',
267
+ message: `${pageName}: frontmatter field "source_paths" must contain only non-empty strings.`,
268
+ });
269
+ }
270
+ }
271
+ // 7. Secret-like content check (run over the full content)
272
+ if (containsSecretLikeContent(normalizedContent)) {
273
+ issues.push({
274
+ level: 'error',
275
+ code: 'secret-like-content',
276
+ message: `${pageName}: content contains secret-like content that cannot be accepted.`,
277
+ });
278
+ }
279
+ return issues;
280
+ }
281
+ /**
282
+ * Parse and validate LLM-generated content as a structured wiki patch.
283
+ *
284
+ * Throws `WikiPatchError` if any error-level lint gate fails. Callers should
285
+ * catch this error to log actionable diagnostics, optionally feed failure
286
+ * details back into the next LLM request, or skip the page.
287
+ *
288
+ * Warnings are attached to the thrown error's `issues` array (when it throws)
289
+ * or are silently surfaced (when the patch is valid). If callers need to
290
+ * inspect warnings on a successful parse, use `validateWikiPatch` instead.
291
+ *
292
+ * @param rawContent - Raw LLM output string to validate.
293
+ * @param pageName - Wiki page slug (e.g. `"Module-Auth"`) used in messages.
294
+ * @returns A validated `WikiPatch` ready for human-notes injection and writing.
295
+ * @throws {WikiPatchError} When one or more error-level issues are found.
296
+ */
297
+ export function parseWikiPatch(rawContent, pageName) {
298
+ const issues = validateWikiPatch(rawContent, pageName);
299
+ const errorCount = issues.filter((i) => i.level === 'error').length;
300
+ if (errorCount > 0) {
301
+ throw new WikiPatchError(`Wiki patch for "${pageName}" failed validation with ${errorCount} error(s).`, pageName, issues);
302
+ }
303
+ const normalized = normalizeLLMOutput(rawContent);
304
+ const { frontmatterRaw, body } = splitFrontmatterAndBody(normalized);
305
+ // frontmatterRaw is guaranteed non-null here (missing-frontmatter would have been an error)
306
+ const fields = parseFrontmatterFields(frontmatterRaw);
307
+ const frontmatter = {
308
+ source_commit: String(fields['source_commit'] ?? ''),
309
+ kind: String(fields['kind'] ?? ''),
310
+ source_paths: Array.isArray(fields['source_paths'])
311
+ ? fields['source_paths'].filter(isNonEmptyString)
312
+ : [],
313
+ compiled_at: String(fields['compiled_at'] ?? ''),
314
+ ...Object.fromEntries(Object.entries(fields).filter(([k]) => !['source_commit', 'kind', 'source_paths', 'compiled_at'].includes(k))),
315
+ };
316
+ return { pageName, content: normalized, frontmatter, body };
317
+ }
318
+ // ── Synthesis pipeline ─────────────────────────────────────────────────────
319
+ /**
320
+ * Call an LLM provider and return the response as a validated `WikiPatch`.
321
+ *
322
+ * Validation runs after every provider response. If a response fails
323
+ * validation and `maxRetries > 0`, the provider is called again. The last
324
+ * thrown `WikiPatchError` is re-thrown when all attempts are exhausted.
325
+ *
326
+ * This makes it impossible for free-form LLM output to bypass patch
327
+ * validation and overwrite wiki pages.
328
+ *
329
+ * @param provider - LLM provider (mock or hosted).
330
+ * @param request - Pre-built `LLMRequest` (use `buildRequest` to assemble).
331
+ * @param options - Optional `{ maxRetries }` (default 0).
332
+ * @returns A validated `WikiPatch`.
333
+ * @throws {WikiPatchError} When all synthesis attempts produce invalid patches.
334
+ * @throws {LLMProviderError} On unrecoverable provider failures.
335
+ * @throws {RangeError} When `maxRetries` is not a non-negative finite number.
336
+ */
337
+ export async function synthesizeWikiPage(provider, request, options = {}) {
338
+ const maxRetries = normalizeMaxRetries(options.maxRetries);
339
+ let lastError;
340
+ let nextRequest = request;
341
+ for (let attempt = 0; attempt <= maxRetries; attempt++) {
342
+ const response = await provider.complete(nextRequest);
343
+ try {
344
+ validateWikiPatchForRequest(response.content, request);
345
+ return parseWikiPatch(response.content, request.pageName);
346
+ }
347
+ catch (err) {
348
+ if (!(err instanceof WikiPatchError))
349
+ throw err;
350
+ lastError = err;
351
+ if (attempt < maxRetries) {
352
+ nextRequest = withValidationFeedback(request, err);
353
+ }
354
+ }
355
+ }
356
+ // All attempts exhausted — re-throw the last validation error
357
+ throw lastError;
358
+ }
359
+ function validateWikiPatchForRequest(rawContent, request) {
360
+ const issues = validateWikiPatch(rawContent, request.pageName);
361
+ if (request.archetype === 'architecture') {
362
+ issues.push(...validateArchitecturePatch(rawContent, request));
363
+ }
364
+ const errorCount = issues.filter((i) => i.level === 'error').length;
365
+ if (errorCount > 0) {
366
+ throw new WikiPatchError(`Wiki patch for "${request.pageName}" failed validation with ${errorCount} error(s).`, request.pageName, issues);
367
+ }
368
+ }
369
+ const ARCHITECTURE_REQUIRED_HEADINGS = [
370
+ '## Executive Architecture Summary',
371
+ '## System and Repository Context',
372
+ '## Major Modules and Responsibilities',
373
+ '## Runtime, Data, and Control-Flow Relationships',
374
+ '## Build, Test, Deployment, and Operational Surfaces',
375
+ '## Cross-Cutting Concerns',
376
+ '## Caveats and Open Questions',
377
+ ];
378
+ function validateArchitecturePatch(rawContent, request) {
379
+ const issues = [];
380
+ const normalizedContent = normalizeLLMOutput(rawContent);
381
+ const { frontmatterRaw, body } = splitFrontmatterAndBody(normalizedContent);
382
+ if (frontmatterRaw === null) {
383
+ return issues;
384
+ }
385
+ const fields = parseFrontmatterFields(frontmatterRaw);
386
+ if (fields['kind'] !== 'architecture') {
387
+ issues.push({
388
+ level: 'error',
389
+ code: 'invalid-architecture-kind',
390
+ message: `${request.pageName}: Architecture page frontmatter must set kind: "architecture".`,
391
+ });
392
+ }
393
+ for (const field of ['confidence', 'claim_status']) {
394
+ const value = fields[field];
395
+ if (!value || typeof value !== 'string' || !value.trim()) {
396
+ issues.push({
397
+ level: 'error',
398
+ code: `missing-${field.replace('_', '-')}`,
399
+ message: `${request.pageName}: Architecture page frontmatter is missing required field "${field}".`,
400
+ });
401
+ }
402
+ }
403
+ const sourcePaths = fields['source_paths'];
404
+ if (sourcePaths === undefined) {
405
+ issues.push({
406
+ level: 'error',
407
+ code: 'missing-source-paths',
408
+ message: `${request.pageName}: Architecture page frontmatter is missing required field "source_paths".`,
409
+ });
410
+ }
411
+ else if (Array.isArray(sourcePaths)) {
412
+ if (sourcePaths.length === 0) {
413
+ issues.push({
414
+ level: 'error',
415
+ code: 'empty-source-paths',
416
+ message: `${request.pageName}: Architecture page source_paths must not be empty.`,
417
+ });
418
+ }
419
+ const allowedSourcePaths = new Set((request.sourcePaths || []).filter(isNonEmptyString));
420
+ const outOfContextPaths = sourcePaths.filter((entry) => isNonEmptyString(entry) && !allowedSourcePaths.has(entry));
421
+ if (outOfContextPaths.length > 0) {
422
+ issues.push({
423
+ level: 'error',
424
+ code: 'out-of-context-source-paths',
425
+ message: `${request.pageName}: Architecture page source_paths must be drawn from the prompt source cards: ${outOfContextPaths.join(', ')}.`,
426
+ });
427
+ }
428
+ }
429
+ for (const heading of ARCHITECTURE_REQUIRED_HEADINGS) {
430
+ if (!body.includes(heading)) {
431
+ issues.push({
432
+ level: 'error',
433
+ code: 'missing-architecture-heading',
434
+ message: `${request.pageName}: Architecture page is missing required heading "${heading}".`,
435
+ });
436
+ }
437
+ }
438
+ const humanNotesBlock = /<!-- HUMAN_NOTES_START -->([\s\S]*?)<!-- HUMAN_NOTES_END -->/.exec(body);
439
+ if (!humanNotesBlock) {
440
+ issues.push({
441
+ level: 'error',
442
+ code: 'missing-human-notes-block',
443
+ message: `${request.pageName}: Architecture page must include a HUMAN_NOTES block.`,
444
+ });
445
+ }
446
+ else if (humanNotesBlock[1].trim().length > 0) {
447
+ issues.push({
448
+ level: 'error',
449
+ code: 'non-empty-human-notes-block',
450
+ message: `${request.pageName}: Architecture page HUMAN_NOTES block must remain empty in synthesized output.`,
451
+ });
452
+ }
453
+ return issues;
454
+ }
455
+ function withValidationFeedback(request, error) {
456
+ return {
457
+ ...request,
458
+ userPrompt: `${request.userPrompt}\n\n${formatValidationFeedback(error)}`,
459
+ };
460
+ }
461
+ function formatValidationFeedback(error) {
462
+ const issueLines = error.issues
463
+ .map((issue) => `- ${issue.level} ${issue.code}: ${issue.message}`)
464
+ .join('\n');
465
+ return [
466
+ 'Previous response was rejected by repo-wiki structured patch validation.',
467
+ 'Validation issues:',
468
+ issueLines || '- error unknown: Validation failed.',
469
+ '',
470
+ 'Retry output contract:',
471
+ '- Output only raw markdown for the page.',
472
+ '- The first line must be exactly `---`.',
473
+ '- Do not include any preamble, commentary, or fenced code block wrapper.',
474
+ '- Include required YAML frontmatter: source_repo, source_commit, compiled_at, kind, page_state, and source_paths.',
475
+ '- source_paths must be a non-empty array of repository source paths grounded in the prompt context.',
476
+ ].join('\n');
477
+ }
478
+ function isNonEmptyString(value) {
479
+ return typeof value === 'string' && value.trim().length > 0;
480
+ }
481
+ function normalizeMaxRetries(maxRetries) {
482
+ if (maxRetries === undefined)
483
+ return 0;
484
+ if (!Number.isFinite(maxRetries) || maxRetries < 0) {
485
+ throw new RangeError('maxRetries must be a non-negative finite number.');
486
+ }
487
+ return Math.floor(maxRetries);
488
+ }
489
+ //# sourceMappingURL=wiki-patch.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"wiki-patch.js","sourceRoot":"","sources":["../../src/wiki-patch.ts"],"names":[],"mappings":"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"}