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.
@@ -22,7 +22,7 @@ function queueHeader() {
22
22
  return [
23
23
  '# LLM Wiki Maintenance Queue',
24
24
  '',
25
- '정식 wiki 문서에 합칠 후보를 보관한다. Hook은 후보만 만들고, agent 기존 durable wiki 문서를 찾아 병합한다.',
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
- eventName === 'UserPromptSubmit'
326
- ? 'LLM Wiki maintenance status:'
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
- ];
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
  }
@@ -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
- const lines = [
446
- 'LLM Wiki maintenance note:',
447
- '- 이전 버전의 llm-wiki-kit 규칙/문서가 남아 있을 수 있다.',
448
- '- 확실히 kit가 관리하는 영역은 자동 갱신된다. 사용자 편집 가능성이 있는 문서는 덮어쓰지 말고 기존 내용을 보존한 채 현재 규칙에 맞게 자연스럽게 정리한다.',
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(`- 자동 갱신 대상: ${outdated.map((file) => file.path).join(', ')}`);
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(`- agent 확인 필요: ${attention.map((file) => file.path).join(', ')}`);
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
- const day = todayKst();
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
- - 평소처럼 Codex 또는 Claude Code 사용한다. 사용자가 별도 \`llm-wiki\` 명령을 외워서 실행해야 하는 흐름을 만들지 않는다.
12
- - 채팅 기억은 임시로 본다. 오래 남길 프로젝트 지식은 \`llm-wiki/\` Markdown에 남긴다.
13
- - \`llm-wiki/raw/\`는 원본 또는 redacted 근거 저장소다. hook envelope append 외에는 원본 capture를 수정하지 않는다.
14
- - \`llm-wiki/wiki/\`는 agent가 관리하는 지식층이다. 결정, 구조, 디버깅, 개념, 절차, 맥락을 여기에 정리한다.
15
- - \`llm-wiki/wiki/memory.md\`는 짧은 핵심 기억이다. 설명 대신 현재 상태와 중요한 문서 링크만 유지한다.
16
- - hook이 주입한 context를 참고하되, 현재 사용자 답변을 먼저 처리한다. 수동 확인이나 정리에는 \`llm-wiki context\`, \`llm-wiki lint\`, \`llm-wiki consolidate\`를 agent 보조 도구로 사용한다.
17
- - hook redacted raw envelope와 필요한 live Q&A를 안전하게 남긴다. \`wiki/queries\`/\`wiki/decisions\` 자동 승격은 기본값이 아니며, durable 지식은 중요도와 동의 흐름에 따라 agent 기존 정식 wiki 문서에 합친다.
18
- - hook은 종료/시작 경계에서 정말 필요한 정리 후보를 \`llm-wiki/outputs/maintenance/queue.md\`에 남길 있다. 정기 maintenance는 agent-side soft reminder이며, pending 항목은 현재 응답을 지연시키지 않는 범위에서 agent가 병합하거나 done/skipped로 표시한다.
19
- - 문서를 만들기 전에 기존 wiki 문서를 먼저 찾아 갱신한다. 반복해서 사실은 \`outputs/questions/\`에만 두지 말고 적절한 wiki 문서에 합친다.
20
- - 일회성 작업 기록은 필요할 \`llm-wiki/outputs/questions/\`에 보존하고, 재사용 가능한 사실/지식은 승인된 경우 \`wiki/architecture/\`, \`wiki/debugging/\`, \`wiki/decisions/\`, \`wiki/concepts/\`, \`procedures/\`에 반영한다.
21
- - 검증 명령, 근거 파일, 불확실한 점을 함께 남긴다. 추론은 추론이라고 표시하고, 모순은 지우지 말고 Open Questions 또는 Contradictions에 남긴다.
22
- - 인증값, token, password, private key, \`.env\` 원문은 저장하지 않는다. 필요한 경우 redacted summary만 남긴다.
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
- Codex와 Claude Code를 평소처럼 사용하는 동안 living Markdown LLM Wiki 자연스럽게 유지한다.
35
- 사용자가 많은 \`llm-wiki\` 명령을 직접 실행하는 방식이 아니라, agent 작업 필요한 wiki 조회와 정리를 수행하되 현재 사용자 답변을 지연시키지 않는 것이 기본이다.
36
- 규칙은 오래된 OMX/OMC/\`omx_wiki/\` 규칙을 대체한다.
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/\`: 원본 또는 redacted 근거 저장소. hook이 redacted envelope를 append하는 경우 외에는 원본 capture를 수정하지 않는다.
40
- - \`wiki/\`: agent가 관리하는 정식 지식 문서. \`wiki/memory.md\`는 hook context에 들어가는 짧은 핵심 기억이다.
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
- - 사용자는 Claude Code/Codex 평소처럼 사용한다. agent 필요한 wiki 조회와 정리를 자연스럽게 수행하되, 현재 사용자 요청에 대한 답변을 먼저 끝낸다.
46
- - \`raw/\` 원본은 수정하지 않는다. 안전한 hook envelope append만 예외다.
47
- - 근거 없는 내용을 사실처럼 쓰지 않는다. 추론은 명시한다.
48
- - 중요한 주장에는 \`source_ids\`, 파일 경로, 검증 명령 중 하나 이상을 남긴다.
49
- - 오래 남길 내용이 생기면 문서부터 만들지 말고 기존 \`wiki/\` 문서를 먼저 찾아 갱신한다.
50
- - 단순 답변, 상태 확인, 일회성 대화는 과도하게 \`wiki/queries\`나 maintenance로 승격하지 않는다.
51
- - 반복해서 지식은 중요도와 동의 흐름에 따라 \`wiki/architecture/\`, \`wiki/debugging/\`, \`wiki/decisions/\`, \`wiki/concepts/\`, \`procedures/\`에 합친다.
52
- - hook이 만든 \`outputs/maintenance/queue.md\` pending 항목은 현재 요청과 관련 있거나 review due 안내가 있을 확인하고, 기존 정식 wiki 문서에 병합한 done 또는 skipped로 표시한다.
53
- - 정기 maintenance 자동 수정이 아니라 agent review다. \`SessionStart\`/\`InstructionsLoaded\`에서만 짧게 안내되고, \`UserPromptSubmit\`에서는 사용자가 wiki/maintenance/정리 관련 질문을 한 경우에만 안내된다.
54
- - \`wiki/memory.md\`는 짧게 유지한다. 설명 대신 현재 상태와 중요한 문서 링크를 둔다.
55
- - 모순은 덮어쓰지 말고 \`Contradictions\` 또는 \`Open Questions\`에 보존한다.
56
- - 인증값, token, password, private key, \`.env\` 원문은 wiki에 저장하지 않는다.
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\`와 \`wiki/index.md\`를 먼저 읽고, 근거를 확인한 기존 wiki 문서를 우선 갱신한다.
79
- - query: hook 주입한 context 참고하되 현재 답변을 먼저 한다. 수동 명령은 점검용이며 일반 사용 흐름의 필수 단계가 아니다.
80
- - lint: 사용자가 요청했거나 wiki 유지보수 작업일 agent가 쓰는 보조 도구다. turn 실행하지 않는다.
81
- - consolidate: agent가 \`memory.md\`/\`index.md\` generated block을 안전하게 갱신할 쓰는 보조 도구다. 손글씨 영역과 정식 문서 본문은 덮어쓰지 않는다.
82
- - maintenance: \`outputs/maintenance/queue.md\`는 종료/시작 경계에서 생긴 정리 후보 목록이다. 현재 요청을 지연시키지 않는 범위에서 agent가 기존 문서 병합 여부를 판단하고 상태를 갱신한다.
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
- 파일은 living wiki 짧은 지도다. 자세한 설명을 길게 쓰기보다, agent가 다음 작업에서 빠르게 찾아갈 entry point를 유지한다.
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) - 짧은 핵심 기억과 주요 entry point.
98
- - [Sources](sources/) - source summary와 source id.
99
- - [Concepts](concepts/) - 재사용 가능한 개념과 용어.
100
- - [Entities](entities/) - 시스템, 모듈, 도구, 서비스, 주요 객체.
101
- - [Decisions](decisions/) - 결정과 근거.
102
- - [Architecture](architecture/) - 구조와 데이터/제어 흐름.
103
- - [Debugging](debugging/) - 원인, 수정, 검증 evidence.
104
- - [Context](context/) - 세션 연속성과 프로젝트 맥락.
105
- - [Queries](queries/) - 재사용 가능한 질문 답변. 일회성 기록은 outputs/questions에 둔다.
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
- - 넓은 질문은 memory index에서 시작한다.
110
- - 문서를 만들기 전에 관련 기존 문서 3-7개를 먼저 확인한다.
111
- - 오래 사실/지식은 기존 정식 문서에 합치고, 일회성 기록은 outputs/questions에 둔다.
112
- - 관련 페이지가 생기면 \`[[page-or-topic]]\` 링크를 추가한다.
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
- Agent가 필요할 \`llm-wiki consolidate --workspace <project>\`로 이 generated block을 갱신한다.
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
- 짧은 핵심 기억이다. hook context 들어갈 만큼 작게 유지하고, 설명을 복사하지 말고 깊은 문서로 링크한다.
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
- Agent가 필요할 \`llm-wiki consolidate --workspace <project>\`로 이 generated block을 갱신한다.
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\`와 \`wiki/index.md\`를 먼저 읽는다.
170
- 2. 근거가 있으면 \`raw/inbox/\` 또는 \`raw/sources/\`를 확인한다.
171
- 3. source별 요약이 필요하면 \`wiki/sources/<slug>.md\`를 만들거나 갱신한다.
172
- 4. 문서부터 만들지 말고 관련 concept/entity/decision/architecture/debugging/context 문서를 먼저 찾아 갱신한다.
173
- 5. 중복 문서를 만들지 않는다. 같은 사실이 이미 있으면 기존 문서에 합친다.
174
- 6. 단순 답변과 일회성 대화는 durable wiki로 승격하지 않는다.
175
- 7. 중요한 주장에는 source reference, confidence, memory type, importance, verification status를 남긴다.
176
- 8. durable entry point가 바뀌면 \`wiki/memory.md\`를 짧게 갱신하거나 agent가 \`llm-wiki consolidate\`를 사용한다.
177
- 9. 의미 있는 변화는 \`wiki/log.md\`에 짧게 남긴다.
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. 현재 사용자 질문에 먼저 답한다. hook 주입한 context 필요한 만큼만 참고한다.
182
- 2. \`wiki/memory.md\`와 \`wiki/index.md\`에서 시작한다.
183
- 3. 관련 \`wiki/\` 문서를 최소한으로 읽는다.
184
- 4. 정확한 근거가 필요할 때만 raw source를 확인한다.
185
- 5. 검증된 사실과 추론을 분리한다.
186
- 6. 수동 확인이 필요할 때만 \`llm-wiki context "<query>"\`를 쓴다. 과거 episodic query/context까지 봐야 때는 \`--include-episodic\`을 붙이고, archived/superseded page까지 봐야 때만 \`--include-archived\`를 붙인다.
187
- 7. 일회성 답변은 durable wiki 승격하지 않는다. 필요한 작업 turn만 \`outputs/questions/\`에 남긴다.
188
- 8. 반복해서 사실/지식은 중요도와 동의 흐름에 따라 \`wiki/architecture/\`, \`wiki/debugging/\`, \`wiki/decisions/\`, \`wiki/concepts/\`, \`procedures/\`에 합친다.
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>\`는 agent 필요할 쓰는 wiki 건강 점검 도구다. 사용자가 매번 실행해야 하는 명령이 아니다.
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
- 점검 대상: stale page, orphan page, broken wiki/Markdown link, unsafe source id, secret-like content, missing source, duplicate concept/title, unsupported claim, unresolved contradiction, outdated managed rule, memory budget, page count growth, hidden episodic/context growth, stale/archived discoverability, maintenance review due.
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
- 정기 maintenance 사용자가 turn 실행할 필요가 없는 agent-side task다. 필요할 agent가 다음 순서로 확인한다:
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 item을 기존 durable page에 병합한 \`done\` 또는 \`skipped\`로 표시한다.
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. 필요할 \`llm-wiki consolidate --workspace <project>\`
209
+ 5. Run \`llm-wiki consolidate --workspace <project>\` when the dry run is acceptable.
203
210
 
204
- 자동 수정은 확실히 kit가 관리하는 영역에만 적용한다. 사용자 편집 가능성이 있는 문서는 덮어쓰지 말고 다음 작업 context에 정리 필요성을 올린다.
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
- - 로컬 프로젝트 wiki에 유용한 작업 맥락은 보존한다.
209
- - 입력이 민감해 보인다는 이유만으로 read/tool call을 막지 않는다.
210
- - token, password, bearer credential, private key, \`.env\` 원문 같은 인증값은 hook payload, summary, context pack, wiki page에 저장하기 전에 redaction한다.
211
- - 민감정보가 wiki에 들어갔을 가능성이 있으면 agent가 \`llm-wiki lint --workspace <project>\`를 사용해 점검한다.
212
- - full raw transcript capture 기본 비활성이다. 프로젝트가 명시적으로 opt-in하고 redaction 경로가 있을 때만 허용한다.
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] || '';
@@ -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
- '- 현재 요청 처리가 우선이며, 현재 runtime 기능은 계속 동작한다.',
120
- `- 업데이트/정비를 수행할 사용할 명령: \`${updateCommand}\``,
121
- '- npm 전역 설치 권한 오류가 나면 환경에 맞게 `npm install -g llm-wiki-kit@latest` 또는 `sudo npm install -g llm-wiki-kit@latest` 같은 update 명령을 다시 실행한다.',
122
- '- status만으로 설치나 업데이트를 실행하지 않는다.',
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