llm-wiki-kit 0.2.10 → 0.2.12
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/README.md +24 -9
- package/docs/concepts.md +6 -5
- package/docs/integrations/claude-code.md +3 -1
- package/docs/integrations/codex.md +3 -2
- package/docs/manual.md +132 -383
- package/docs/operations.md +4 -1
- package/package.json +12 -2
- package/src/capture-policy.js +30 -23
- package/src/cli.js +17 -2
- package/src/hook.js +15 -7
- package/src/language.js +73 -0
- package/src/live-qa.js +321 -0
- package/src/maintenance.js +13 -8
- package/src/project-state.js +20 -9
- package/src/project.js +7 -29
- package/src/templates.js +89 -82
- package/src/update-notice.js +14 -4
- package/src/wiki-lint.js +49 -0
- package/src/wiki-search.js +35 -13
package/src/maintenance.js
CHANGED
|
@@ -22,7 +22,7 @@ function queueHeader() {
|
|
|
22
22
|
return [
|
|
23
23
|
'# LLM Wiki Maintenance Queue',
|
|
24
24
|
'',
|
|
25
|
-
'
|
|
25
|
+
'Candidates to merge into durable wiki pages. Hooks only create candidates; the active agent reviews and merges them into existing durable wiki documents.',
|
|
26
26
|
'',
|
|
27
27
|
'Status values: pending, done, skipped.',
|
|
28
28
|
'',
|
|
@@ -309,6 +309,7 @@ export async function recoverStaleTurnStates(projectRoot, options = {}) {
|
|
|
309
309
|
|
|
310
310
|
export function formatMaintenanceContext(summary, options = {}) {
|
|
311
311
|
if (!summary.reviewDue) return '';
|
|
312
|
+
const language = options.language === 'ko' ? 'ko' : 'en';
|
|
312
313
|
const eventName = options.eventName || '';
|
|
313
314
|
const defaultLimit = eventName === 'SessionStart' || eventName === 'InstructionsLoaded' ? 1 : 5;
|
|
314
315
|
const limit = options.limit || defaultLimit;
|
|
@@ -321,13 +322,17 @@ export function formatMaintenanceContext(summary, options = {}) {
|
|
|
321
322
|
return '';
|
|
322
323
|
}
|
|
323
324
|
|
|
324
|
-
const lines =
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
325
|
+
const lines = language === 'ko'
|
|
326
|
+
? [
|
|
327
|
+
'LLM Wiki maintenance status:',
|
|
328
|
+
`- review due: yes (${(summary.reviewReasons || []).slice(0, 2).join('; ') || 'periodic review threshold met'}).`,
|
|
329
|
+
`- pending review items: ${summary.pendingCount}. 현재 요청이 우선이며, 관련 있을 때만 durable wiki 정리에 사용한다.`,
|
|
330
|
+
]
|
|
331
|
+
: [
|
|
332
|
+
'LLM Wiki maintenance status:',
|
|
333
|
+
`- review due: yes (${(summary.reviewReasons || []).slice(0, 2).join('; ') || 'periodic review threshold met'}).`,
|
|
334
|
+
`- pending review items: ${summary.pendingCount}. The current request comes first; use this only when it is relevant to durable wiki cleanup.`,
|
|
335
|
+
];
|
|
331
336
|
for (const item of pending) {
|
|
332
337
|
lines.push(`- ${item.topic || item.id}: ${item.suggested_target}; source=${item.source}${item.result_missing ? '; result missing' : ''}`);
|
|
333
338
|
}
|
package/src/project-state.js
CHANGED
|
@@ -436,22 +436,33 @@ export async function inspectProjectState(projectRoot) {
|
|
|
436
436
|
};
|
|
437
437
|
}
|
|
438
438
|
|
|
439
|
-
export function formatProjectMaintenanceContext(inspection) {
|
|
439
|
+
export function formatProjectMaintenanceContext(inspection, options = {}) {
|
|
440
440
|
const files = inspection?.managedFiles || [];
|
|
441
441
|
const attention = files.filter((file) => file.needsAttention);
|
|
442
442
|
const outdated = files.filter((file) => !file.current && file.patchable);
|
|
443
443
|
if (attention.length === 0 && outdated.length === 0) return '';
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
444
|
+
const language = options.language === 'ko' ? 'ko' : 'en';
|
|
445
|
+
|
|
446
|
+
const lines = language === 'ko'
|
|
447
|
+
? [
|
|
448
|
+
'LLM Wiki maintenance note:',
|
|
449
|
+
'- 이전 버전의 llm-wiki-kit 규칙/문서가 남아 있을 수 있다.',
|
|
450
|
+
'- 확실히 kit가 관리하는 영역은 자동 갱신된다. 사용자 편집 가능성이 있는 문서는 덮어쓰지 말고 기존 내용을 보존한 채 현재 규칙에 맞게 자연스럽게 정리한다.',
|
|
451
|
+
]
|
|
452
|
+
: [
|
|
453
|
+
'LLM Wiki maintenance note:',
|
|
454
|
+
'- Older llm-wiki-kit rules or docs may still be present.',
|
|
455
|
+
'- Clearly managed kit areas are refreshed automatically. Preserve user-edited files and align them with current rules without overwriting local content.',
|
|
456
|
+
];
|
|
450
457
|
if (outdated.length > 0) {
|
|
451
|
-
lines.push(
|
|
458
|
+
lines.push(language === 'ko'
|
|
459
|
+
? `- 자동 갱신 대상: ${outdated.map((file) => file.path).join(', ')}`
|
|
460
|
+
: `- auto-refresh candidates: ${outdated.map((file) => file.path).join(', ')}`);
|
|
452
461
|
}
|
|
453
462
|
if (attention.length > 0) {
|
|
454
|
-
lines.push(
|
|
463
|
+
lines.push(language === 'ko'
|
|
464
|
+
? `- agent 확인 필요: ${attention.map((file) => file.path).join(', ')}`
|
|
465
|
+
: `- needs agent review: ${attention.map((file) => file.path).join(', ')}`);
|
|
455
466
|
}
|
|
456
467
|
return lines.join('\n');
|
|
457
468
|
}
|
package/src/project.js
CHANGED
|
@@ -14,6 +14,7 @@ import { normalizeForStorage, redactText, summarizeForStorage } from './redactio
|
|
|
14
14
|
import { gitignore, indexPage, llmWikiAgents, logPage, memoryPage, procedure, rootAgentsPolicy } from './templates.js';
|
|
15
15
|
import { formatProjectMaintenanceContext, inspectProjectState, recordManagedTemplates } from './project-state.js';
|
|
16
16
|
import { buildContextPack, formatHookContextPack, searchWiki as searchWikiWithIndex } from './wiki-search.js';
|
|
17
|
+
import { appendLiveQa as appendChunkedLiveQa } from './live-qa.js';
|
|
17
18
|
|
|
18
19
|
export async function bootstrapProject(projectRoot, options = {}) {
|
|
19
20
|
if (process.env.LLM_WIKI_KIT_DISABLE_BOOTSTRAP === '1') return { created: false };
|
|
@@ -97,32 +98,7 @@ function hasCapturedQuestion(entry) {
|
|
|
97
98
|
}
|
|
98
99
|
|
|
99
100
|
export async function appendLiveQa(projectRoot, entry) {
|
|
100
|
-
|
|
101
|
-
const path = join(projectRoot, 'llm-wiki', 'outputs', 'questions', `${day}-live-qa.md`);
|
|
102
|
-
const block = [
|
|
103
|
-
`\n## ${timeKst()} KST - ${entry.topic || 'session turn'}`,
|
|
104
|
-
'',
|
|
105
|
-
'### Question',
|
|
106
|
-
entry.question || '(not captured)',
|
|
107
|
-
'',
|
|
108
|
-
'### Work',
|
|
109
|
-
entry.work || '(not captured)',
|
|
110
|
-
'',
|
|
111
|
-
'### Result',
|
|
112
|
-
entry.result || '(not captured)',
|
|
113
|
-
'',
|
|
114
|
-
'### Changed files',
|
|
115
|
-
entry.changedFiles || '(not captured)',
|
|
116
|
-
'',
|
|
117
|
-
'### Verification',
|
|
118
|
-
entry.verification || '(not captured)',
|
|
119
|
-
'',
|
|
120
|
-
'### Follow-up',
|
|
121
|
-
entry.followUp || '다음 작업에서 이 turn의 reusable fact가 있으면 기존 wiki 문서에 합치고, 일회성 기록은 이 Q&A에만 보존한다.',
|
|
122
|
-
'',
|
|
123
|
-
].join('\n');
|
|
124
|
-
await appendText(path, redactText(block, 12000));
|
|
125
|
-
return path;
|
|
101
|
+
return appendChunkedLiveQa(projectRoot, entry);
|
|
126
102
|
}
|
|
127
103
|
|
|
128
104
|
export async function writeQueryPage(projectRoot, entry) {
|
|
@@ -160,19 +136,21 @@ export async function searchWiki(projectRoot, query, limit = 5) {
|
|
|
160
136
|
return searchWikiWithIndex(projectRoot, query, typeof limit === 'number' ? { limit } : limit);
|
|
161
137
|
}
|
|
162
138
|
|
|
163
|
-
export async function buildContextBrief(projectRoot, eventName, query = '') {
|
|
139
|
+
export async function buildContextBrief(projectRoot, eventName, query = '', options = {}) {
|
|
140
|
+
const language = options.language === 'ko' ? 'ko' : 'en';
|
|
164
141
|
const pack = await buildContextPack(projectRoot, query, {
|
|
165
142
|
includeLog: eventName === 'SessionStart',
|
|
166
143
|
limit: 5,
|
|
167
144
|
});
|
|
168
145
|
const maintenance = await inspectProjectState(projectRoot)
|
|
169
|
-
.then(formatProjectMaintenanceContext)
|
|
146
|
+
.then((inspection) => formatProjectMaintenanceContext(inspection, { language }))
|
|
170
147
|
.catch(() => '');
|
|
171
148
|
const wikiMaintenance = await maintenanceSummary(projectRoot)
|
|
172
|
-
.then((summary) => formatMaintenanceContext(summary, { eventName, query }))
|
|
149
|
+
.then((summary) => formatMaintenanceContext(summary, { eventName, query, language }))
|
|
173
150
|
.catch(() => '');
|
|
174
151
|
return [formatHookContextPack(pack, {
|
|
175
152
|
eventName,
|
|
153
|
+
language,
|
|
176
154
|
hitLimit: eventName === 'SessionStart' ? 2 : 3,
|
|
177
155
|
logLineLimit: eventName === 'SessionStart' ? 2 : 0,
|
|
178
156
|
}), maintenance, wikiMaintenance].filter(Boolean).join('\n\n');
|
package/src/templates.js
CHANGED
|
@@ -8,18 +8,19 @@ export function rootAgentsPolicy() {
|
|
|
8
8
|
This repository uses llm-wiki-kit as a hook-first living Markdown wiki for Codex and Claude Code.
|
|
9
9
|
|
|
10
10
|
- This block supersedes older OMX/OMC/\`omx_wiki/\` LLM Wiki instructions for this repository.
|
|
11
|
-
-
|
|
12
|
-
-
|
|
13
|
-
-
|
|
14
|
-
- \`llm-wiki/
|
|
15
|
-
- \`llm-wiki/wiki
|
|
16
|
-
-
|
|
17
|
-
- hook
|
|
18
|
-
-
|
|
19
|
-
-
|
|
20
|
-
-
|
|
21
|
-
-
|
|
22
|
-
-
|
|
11
|
+
- Use Codex or Claude Code normally. Do not create a workflow where users must remember extra \`llm-wiki\` commands during ordinary work.
|
|
12
|
+
- Language: respond in the user's current prompt language when it is clearly Korean or English. Keep technical identifiers, commands, paths, code, and original error text unchanged. If no prompt language is clear, follow local \`CLAUDE.md\`/\`AGENTS.md\` guidance, then fall back to English.
|
|
13
|
+
- Treat chat memory as temporary. Durable project knowledge belongs in repository Markdown under \`llm-wiki/\`.
|
|
14
|
+
- \`llm-wiki/raw/\` is the immutable or redacted evidence layer. Do not modify raw captures except safe hook envelope append.
|
|
15
|
+
- \`llm-wiki/wiki/\` is the curated knowledge layer managed by the agent. Put decisions, architecture, debugging findings, concepts, procedures, and context there.
|
|
16
|
+
- Keep \`llm-wiki/wiki/memory.md\` short. Link to important documents instead of copying long explanations.
|
|
17
|
+
- Use hook-injected context when helpful, but answer the current user request first. Use \`llm-wiki context\`, \`llm-wiki lint\`, and \`llm-wiki consolidate\` only as agent maintenance helpers.
|
|
18
|
+
- Hooks safely store redacted raw envelopes and work/decision-focused live Q&A. Simple answers, status checks, and keyword-only turns should not be promoted to live Q&A or durable wiki by default.
|
|
19
|
+
- Hooks may queue durable cleanup candidates in \`llm-wiki/outputs/maintenance/queue.md\` at stop/start boundaries. Treat maintenance as a soft agent-side reminder; merge pending items only when relevant and mark them \`done\` or \`skipped\`.
|
|
20
|
+
- Before creating new wiki pages, search existing pages and update the right one when possible. Reusable facts should not stay only in chunked \`outputs/questions/\`.
|
|
21
|
+
- Store one-off work or decision records in \`llm-wiki/outputs/questions/YYYY-MM-DD/live-qa-001.md\` when needed. Merge reusable knowledge into \`wiki/architecture/\`, \`wiki/debugging/\`, \`wiki/decisions/\`, \`wiki/concepts/\`, or \`procedures/\` when approved or clearly important.
|
|
22
|
+
- Record verification commands, evidence files, and uncertainty. Mark inference explicitly and preserve contradictions in Open Questions or Contradictions.
|
|
23
|
+
- Never store credentials, tokens, passwords, private keys, or raw \`.env\` contents. Store only redacted summaries when needed.
|
|
23
24
|
|
|
24
25
|
<!-- llm-wiki-kit:end -->
|
|
25
26
|
`;
|
|
@@ -31,29 +32,35 @@ export function llmWikiAgents() {
|
|
|
31
32
|
Generated by llm-wiki-kit ${runtimeVersion()}.
|
|
32
33
|
|
|
33
34
|
## Purpose
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
35
|
+
Maintain a living Markdown LLM Wiki while users work normally in Codex or Claude Code.
|
|
36
|
+
The user should not need to run many \`llm-wiki\` commands manually. The agent checks and maintains wiki context when useful, but the current user answer comes first.
|
|
37
|
+
These rules replace older OMX/OMC/\`omx_wiki/\` rules for this project.
|
|
38
|
+
|
|
39
|
+
## Language
|
|
40
|
+
- Follow the user's current prompt language when it is clearly Korean or English.
|
|
41
|
+
- If no current prompt language is clear, follow local \`CLAUDE.md\`/\`AGENTS.md\` guidance, then fall back to English.
|
|
42
|
+
- Keep commands, paths, code identifiers, API names, package names, logs, and original error text unchanged.
|
|
43
|
+
- Korean and English users should both be able to use Codex/Claude Code naturally without changing \`llm-wiki\` commands.
|
|
37
44
|
|
|
38
45
|
## Directories
|
|
39
|
-
- \`raw/\`:
|
|
40
|
-
- \`wiki/\`:
|
|
41
|
-
- \`outputs/\`: live Q&A,
|
|
42
|
-
- \`procedures/\`: ingest, query, lint, security
|
|
46
|
+
- \`raw/\`: immutable or redacted evidence. Do not edit raw captures except safe hook envelope append.
|
|
47
|
+
- \`wiki/\`: curated knowledge pages maintained by the agent. \`wiki/memory.md\` is the short hot index injected into hook context.
|
|
48
|
+
- \`outputs/\`: live Q&A, reports, maintenance candidates, and long generated artifacts. One-off records belong here.
|
|
49
|
+
- \`procedures/\`: operating rules for ingest, query, lint, and security.
|
|
43
50
|
|
|
44
51
|
## Core Rules
|
|
45
|
-
-
|
|
46
|
-
- \`raw/\`
|
|
47
|
-
-
|
|
48
|
-
-
|
|
49
|
-
-
|
|
50
|
-
-
|
|
51
|
-
-
|
|
52
|
-
-
|
|
53
|
-
-
|
|
54
|
-
- \`wiki/memory.md
|
|
55
|
-
-
|
|
56
|
-
-
|
|
52
|
+
- Users work normally in Claude Code/Codex. The agent performs wiki lookup and maintenance naturally, but answers the current request first.
|
|
53
|
+
- Do not modify \`raw/\` source material except safe hook envelope append.
|
|
54
|
+
- Do not state unsupported claims as facts. Mark inference explicitly.
|
|
55
|
+
- Important claims should include at least one of: \`source_ids\`, file paths, or verification commands.
|
|
56
|
+
- When durable knowledge appears, search existing \`wiki/\` pages before creating a new page.
|
|
57
|
+
- Do not promote simple answers, status checks, keyword-only replies, or one-off chat into live Q&A, \`wiki/queries\`, or maintenance.
|
|
58
|
+
- Merge reusable knowledge into \`wiki/architecture/\`, \`wiki/debugging/\`, \`wiki/decisions/\`, \`wiki/concepts/\`, or \`procedures/\` based on importance and user consent flow.
|
|
59
|
+
- Review \`outputs/maintenance/queue.md\` pending items only when related to the current request or when review is due. Merge into existing durable wiki pages, then mark items \`done\` or \`skipped\`.
|
|
60
|
+
- Periodic maintenance is agent review, not automatic editing. Show only short reminders at \`SessionStart\`/\`InstructionsLoaded\`, and only show prompt-time reminders for wiki/maintenance-related user prompts.
|
|
61
|
+
- Keep \`wiki/memory.md\` short. Use links to current state and important documents instead of long explanations.
|
|
62
|
+
- Preserve contradictions in \`Contradictions\` or \`Open Questions\`; do not overwrite them silently.
|
|
63
|
+
- Do not store credentials, tokens, passwords, private keys, or raw \`.env\` contents in wiki.
|
|
57
64
|
|
|
58
65
|
## Page Format
|
|
59
66
|
Use YAML frontmatter when creating wiki pages:
|
|
@@ -75,11 +82,11 @@ superseded_by: []
|
|
|
75
82
|
\`\`\`
|
|
76
83
|
|
|
77
84
|
## Operations
|
|
78
|
-
- ingest: \`wiki/memory.md
|
|
79
|
-
- query: hook
|
|
80
|
-
- lint:
|
|
81
|
-
- consolidate:
|
|
82
|
-
- maintenance: \`outputs/maintenance/queue.md
|
|
85
|
+
- ingest: read \`wiki/memory.md\` and \`wiki/index.md\` first, verify new evidence, then prefer updating existing wiki pages.
|
|
86
|
+
- query: use hook-injected context when useful, but answer the current request first. Manual commands are diagnostics, not required daily workflow.
|
|
87
|
+
- lint: agent helper for user-requested or wiki maintenance work. Do not run it every turn.
|
|
88
|
+
- consolidate: safely refresh generated blocks in \`memory.md\`/\`index.md\`. Do not overwrite handwritten sections or curated document bodies.
|
|
89
|
+
- maintenance: \`outputs/maintenance/queue.md\` stores stop/start cleanup candidates. Review and update it only when it does not delay the current user request.
|
|
83
90
|
`;
|
|
84
91
|
}
|
|
85
92
|
|
|
@@ -90,31 +97,31 @@ Generated by llm-wiki-kit.
|
|
|
90
97
|
|
|
91
98
|
## Overview
|
|
92
99
|
|
|
93
|
-
|
|
100
|
+
This file is the short navigation map for the living wiki. Keep entry points easy to scan instead of adding long explanations here.
|
|
94
101
|
|
|
95
102
|
## Main Areas
|
|
96
103
|
|
|
97
|
-
- [Memory](memory.md) -
|
|
98
|
-
- [Sources](sources/) - source
|
|
99
|
-
- [Concepts](concepts/) -
|
|
100
|
-
- [Entities](entities/) -
|
|
101
|
-
- [Decisions](decisions/) -
|
|
102
|
-
- [Architecture](architecture/) -
|
|
103
|
-
- [Debugging](debugging/) -
|
|
104
|
-
- [Context](context/) -
|
|
105
|
-
- [Queries](queries/) -
|
|
104
|
+
- [Memory](memory.md) - short active memory and durable entry points.
|
|
105
|
+
- [Sources](sources/) - source summaries and source IDs.
|
|
106
|
+
- [Concepts](concepts/) - reusable concepts and terminology.
|
|
107
|
+
- [Entities](entities/) - systems, modules, tools, services, and important objects.
|
|
108
|
+
- [Decisions](decisions/) - decisions and rationale.
|
|
109
|
+
- [Architecture](architecture/) - structure, data flow, and control flow.
|
|
110
|
+
- [Debugging](debugging/) - causes, fixes, and verification evidence.
|
|
111
|
+
- [Context](context/) - session continuity and project context.
|
|
112
|
+
- [Queries](queries/) - reusable question answers. One-off records belong in outputs/questions.
|
|
106
113
|
|
|
107
114
|
## Operating Notes
|
|
108
115
|
|
|
109
|
-
-
|
|
110
|
-
-
|
|
111
|
-
-
|
|
112
|
-
-
|
|
116
|
+
- Start broad questions from memory and this index.
|
|
117
|
+
- Before creating a new page, check 3-7 relevant existing pages.
|
|
118
|
+
- Merge durable facts into existing curated pages. Keep one-off work/decision records in chunked outputs/questions.
|
|
119
|
+
- Add \`[[page-or-topic]]\` links when related pages become useful.
|
|
113
120
|
|
|
114
121
|
<!-- llm-wiki-kit:index-start -->
|
|
115
122
|
## Generated Page Map
|
|
116
123
|
|
|
117
|
-
|
|
124
|
+
The agent may refresh this generated block with \`llm-wiki consolidate --workspace <project>\`.
|
|
118
125
|
<!-- llm-wiki-kit:index-end -->
|
|
119
126
|
`;
|
|
120
127
|
}
|
|
@@ -136,11 +143,11 @@ superseded_by: []
|
|
|
136
143
|
|
|
137
144
|
# LLM Wiki Memory
|
|
138
145
|
|
|
139
|
-
|
|
146
|
+
Short active memory for hook context. Keep it small and link to deeper documents instead of copying long explanations.
|
|
140
147
|
|
|
141
148
|
## Current Focus
|
|
142
149
|
|
|
143
|
-
-
|
|
150
|
+
- Add the current durable project focus here in a few short bullets.
|
|
144
151
|
|
|
145
152
|
## Durable Entry Points
|
|
146
153
|
|
|
@@ -150,7 +157,7 @@ superseded_by: []
|
|
|
150
157
|
<!-- llm-wiki-kit:memory-start -->
|
|
151
158
|
## Generated Memory Map
|
|
152
159
|
|
|
153
|
-
|
|
160
|
+
The agent may refresh this generated block with \`llm-wiki consolidate --workspace <project>\`.
|
|
154
161
|
<!-- llm-wiki-kit:memory-end -->
|
|
155
162
|
`;
|
|
156
163
|
}
|
|
@@ -166,50 +173,50 @@ export function procedure(name) {
|
|
|
166
173
|
const procedures = {
|
|
167
174
|
'ingest.md': `# Ingest Procedure
|
|
168
175
|
|
|
169
|
-
1. \`wiki/memory.md
|
|
170
|
-
2.
|
|
171
|
-
3.
|
|
172
|
-
4.
|
|
173
|
-
5.
|
|
174
|
-
6.
|
|
175
|
-
7.
|
|
176
|
-
8. durable entry
|
|
177
|
-
9.
|
|
176
|
+
1. Read \`wiki/memory.md\` and \`wiki/index.md\` first.
|
|
177
|
+
2. If new evidence exists, inspect \`raw/inbox/\` or \`raw/sources/\`.
|
|
178
|
+
3. Create or update \`wiki/sources/<slug>.md\` only when a source summary is useful.
|
|
179
|
+
4. Before creating a new page, look for related concept/entity/decision/architecture/debugging/context pages and update those first.
|
|
180
|
+
5. Do not create duplicates. Merge facts into existing pages when they already exist.
|
|
181
|
+
6. Do not promote simple answers or one-off chat into durable wiki.
|
|
182
|
+
7. Important claims should record source references, confidence, memory type, importance, and verification status.
|
|
183
|
+
8. When durable entry points change, update \`wiki/memory.md\` briefly or use \`llm-wiki consolidate\`.
|
|
184
|
+
9. Add a short entry to \`wiki/log.md\` for meaningful wiki changes.
|
|
178
185
|
`,
|
|
179
186
|
'query.md': `# Query Procedure
|
|
180
187
|
|
|
181
|
-
1.
|
|
182
|
-
2. \`wiki/memory.md
|
|
183
|
-
3.
|
|
184
|
-
4.
|
|
185
|
-
5.
|
|
186
|
-
6.
|
|
187
|
-
7.
|
|
188
|
-
8.
|
|
188
|
+
1. Answer the current user question first. Use hook-injected context only as needed.
|
|
189
|
+
2. Start from \`wiki/memory.md\` and \`wiki/index.md\`.
|
|
190
|
+
3. Read the smallest relevant set of \`wiki/\` documents.
|
|
191
|
+
4. Inspect raw sources only when exact evidence matters.
|
|
192
|
+
5. Separate verified facts from inference.
|
|
193
|
+
6. Use \`llm-wiki context "<query>"\` only when manual inspection is useful. Add \`--include-episodic\` only for historical query/context pages, and \`--include-archived\` only for archived/superseded pages.
|
|
194
|
+
7. Do not promote one-off answers, status checks, or keyword-only replies to durable wiki or live Q&A. Archive only work turns with tool evidence, changed-file evidence, verification, or structured decision/debugging conclusions.
|
|
195
|
+
8. Merge reusable facts into \`wiki/architecture/\`, \`wiki/debugging/\`, \`wiki/decisions/\`, \`wiki/concepts/\`, or \`procedures/\` based on importance and user consent flow.
|
|
189
196
|
`,
|
|
190
197
|
'lint.md': `# Lint Procedure
|
|
191
198
|
|
|
192
|
-
\`llm-wiki lint --workspace <project
|
|
199
|
+
\`llm-wiki lint --workspace <project>\` is an agent-side wiki health check. Users should not need to run it every turn.
|
|
193
200
|
|
|
194
|
-
|
|
201
|
+
Checks include stale pages, orphan pages, broken wiki/Markdown links, unsafe source IDs, secret-like content, missing sources, duplicate concepts/titles, unsupported claims, unresolved contradictions, outdated managed rules, memory budget pressure, page-count growth, hidden episodic/context growth, stale/archived discoverability, maintenance review due, oversized legacy live Q&A, and oversized live Q&A chunks.
|
|
195
202
|
|
|
196
|
-
|
|
203
|
+
Periodic maintenance is an agent-side task, not a per-turn user command. When needed, the agent checks:
|
|
197
204
|
|
|
198
205
|
1. \`llm-wiki lint --workspace <project>\`
|
|
199
206
|
2. \`llm-wiki maintenance --workspace <project>\`
|
|
200
|
-
3. pending
|
|
207
|
+
3. Merge pending items into existing durable pages, then mark them \`done\` or \`skipped\`.
|
|
201
208
|
4. \`llm-wiki consolidate --workspace <project> --dry-run\`
|
|
202
|
-
5.
|
|
209
|
+
5. Run \`llm-wiki consolidate --workspace <project>\` when the dry run is acceptable.
|
|
203
210
|
|
|
204
|
-
|
|
211
|
+
Apply automatic fixes only to clearly managed kit areas. Do not overwrite user-editable documents; surface cleanup needs in the next work context.
|
|
205
212
|
`,
|
|
206
213
|
'security.md': `# Security Procedure
|
|
207
214
|
|
|
208
|
-
-
|
|
209
|
-
-
|
|
210
|
-
-
|
|
211
|
-
-
|
|
212
|
-
-
|
|
215
|
+
- Preserve useful local project work context.
|
|
216
|
+
- Do not block reads or tool calls only because input looks sensitive.
|
|
217
|
+
- Redact authentication values such as tokens, passwords, bearer credentials, private keys, and raw \`.env\` contents before writing hook payloads, summaries, context packs, or wiki pages.
|
|
218
|
+
- If sensitive material may have entered the wiki, use \`llm-wiki lint --workspace <project>\`.
|
|
219
|
+
- Full raw transcript capture is disabled by default. Allow it only when a project explicitly opts in and has a redaction path.
|
|
213
220
|
`,
|
|
214
221
|
};
|
|
215
222
|
return procedures[name] || '';
|
package/src/update-notice.js
CHANGED
|
@@ -113,12 +113,22 @@ export async function updateNoticeContext(projectRoot, eventName, options = {})
|
|
|
113
113
|
|
|
114
114
|
const workspace = resolve(projectRoot || process.cwd());
|
|
115
115
|
const updateCommand = commandForProject('update', workspace);
|
|
116
|
+
if (options.language === 'ko') {
|
|
117
|
+
return [
|
|
118
|
+
'LLM Wiki runtime update status:',
|
|
119
|
+
`- current hook runtime: ${notice.installedVersion}; npm registry: ${notice.latestVersion}`,
|
|
120
|
+
'- 현재 요청 처리가 우선이며, 현재 runtime 기능은 계속 동작한다.',
|
|
121
|
+
`- 업데이트/정비를 수행할 때 사용할 명령: \`${updateCommand}\``,
|
|
122
|
+
'- npm 전역 설치 권한 오류가 나면 환경에 맞게 `npm install -g llm-wiki-kit@latest` 또는 `sudo npm install -g llm-wiki-kit@latest` 후 같은 update 명령을 다시 실행한다.',
|
|
123
|
+
'- 이 status만으로 설치나 업데이트를 실행하지 않는다.',
|
|
124
|
+
].join('\n');
|
|
125
|
+
}
|
|
116
126
|
return [
|
|
117
127
|
'LLM Wiki runtime update status:',
|
|
118
128
|
`- current hook runtime: ${notice.installedVersion}; npm registry: ${notice.latestVersion}`,
|
|
119
|
-
'-
|
|
120
|
-
`-
|
|
121
|
-
'- npm
|
|
122
|
-
'-
|
|
129
|
+
'- The current request comes first, and the current runtime continues to work.',
|
|
130
|
+
`- Use this command only when performing update or maintenance work: \`${updateCommand}\``,
|
|
131
|
+
'- If global npm install hits a permission error, run `npm install -g llm-wiki-kit@latest` or `sudo npm install -g llm-wiki-kit@latest` as appropriate, then rerun the same update command.',
|
|
132
|
+
'- Do not install or update only because this status is present.',
|
|
123
133
|
].join('\n');
|
|
124
134
|
}
|
package/src/wiki-lint.js
CHANGED
|
@@ -4,6 +4,7 @@ import { exists, readText } from './fs-utils.js';
|
|
|
4
4
|
import { maintenanceSummary } from './maintenance.js';
|
|
5
5
|
import { inspectProjectState } from './project-state.js';
|
|
6
6
|
import { hasSecretLikeText } from './redaction.js';
|
|
7
|
+
import { liveQaMaxBytes, liveQaMaxLines } from './live-qa.js';
|
|
7
8
|
import {
|
|
8
9
|
buildAliasMap,
|
|
9
10
|
buildWikiGraph,
|
|
@@ -41,11 +42,57 @@ const CORE_PAGES = new Set(['wiki/index.md', 'wiki/log.md', 'wiki/memory.md']);
|
|
|
41
42
|
const MEMORY_NEAR_BUDGET_BYTES = 20 * 1024;
|
|
42
43
|
const HIDDEN_PAGE_WARNING_THRESHOLD = 50;
|
|
43
44
|
const SEARCH_CAP_WARNING_RATIO = 0.8;
|
|
45
|
+
const ARCHIVED_LIVE_QA_MARKER = '<!-- llm-wiki-kit:archived-live-qa -->';
|
|
44
46
|
|
|
45
47
|
function issue(severity, code, path, message) {
|
|
46
48
|
return { severity, code, path, message };
|
|
47
49
|
}
|
|
48
50
|
|
|
51
|
+
function countLines(text) {
|
|
52
|
+
if (!text) return 0;
|
|
53
|
+
return String(text).split(/\r?\n/).length;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
function liveQaOversized(text) {
|
|
57
|
+
return countLines(text) > liveQaMaxLines() || Buffer.byteLength(text || '', 'utf8') > liveQaMaxBytes();
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
async function liveQaGrowthIssues(projectRoot) {
|
|
61
|
+
const issues = [];
|
|
62
|
+
const root = join(projectRoot, 'llm-wiki', 'outputs', 'questions');
|
|
63
|
+
let entries = [];
|
|
64
|
+
try {
|
|
65
|
+
entries = await readdir(root, { withFileTypes: true });
|
|
66
|
+
} catch {
|
|
67
|
+
return issues;
|
|
68
|
+
}
|
|
69
|
+
for (const entry of entries) {
|
|
70
|
+
const full = join(root, entry.name);
|
|
71
|
+
if (entry.isFile() && /^\d{4}-\d{2}-\d{2}-live-qa\.md$/.test(entry.name)) {
|
|
72
|
+
const text = await readText(full, '');
|
|
73
|
+
if (!text.includes(ARCHIVED_LIVE_QA_MARKER) && liveQaOversized(text)) {
|
|
74
|
+
issues.push(issue('warning', 'live-qa-legacy-oversized', `outputs/questions/${entry.name}`, 'legacy daily live Q&A file is oversized; run archive-questions to split it into chunks'));
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
if (entry.isDirectory() && /^\d{4}-\d{2}-\d{2}$/.test(entry.name)) {
|
|
78
|
+
let chunkEntries = [];
|
|
79
|
+
try {
|
|
80
|
+
chunkEntries = await readdir(full, { withFileTypes: true });
|
|
81
|
+
} catch {
|
|
82
|
+
chunkEntries = [];
|
|
83
|
+
}
|
|
84
|
+
for (const chunk of chunkEntries) {
|
|
85
|
+
if (!chunk.isFile() || !/^live-qa-\d+\.md$/.test(chunk.name)) continue;
|
|
86
|
+
const text = await readText(join(full, chunk.name), '');
|
|
87
|
+
if (liveQaOversized(text)) {
|
|
88
|
+
issues.push(issue('warning', 'live-qa-chunk-oversized', `outputs/questions/${entry.name}/${chunk.name}`, 'live Q&A chunk exceeds the configured rollover budget'));
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
return issues;
|
|
94
|
+
}
|
|
95
|
+
|
|
49
96
|
function isDateLike(value) {
|
|
50
97
|
return value === 'unknown' || /^\d{4}-\d{2}-\d{2}$/.test(String(value || ''));
|
|
51
98
|
}
|
|
@@ -291,6 +338,8 @@ export async function runLint(projectRoot, options = {}) {
|
|
|
291
338
|
}
|
|
292
339
|
}
|
|
293
340
|
|
|
341
|
+
issues.push(...await liveQaGrowthIssues(projectRoot));
|
|
342
|
+
|
|
294
343
|
return lintResult(projectRoot, pages, issues);
|
|
295
344
|
}
|
|
296
345
|
|