kirograph 1.2.2 → 1.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (45) hide show
  1. package/README.md +4 -3
  2. package/dist/bin/commands/attack-surface.js +15 -2
  3. package/dist/bin/commands/attack-surface.js.map +2 -2
  4. package/dist/bin/commands/help.js +4 -2
  5. package/dist/bin/commands/help.js.map +2 -2
  6. package/dist/bin/commands/memory.js +23 -3
  7. package/dist/bin/commands/memory.js.map +2 -2
  8. package/dist/bin/commands/security-export.js +7 -1
  9. package/dist/bin/commands/security-export.js.map +2 -2
  10. package/dist/bin/commands/wiki.js +12 -1
  11. package/dist/bin/commands/wiki.js.map +2 -2
  12. package/dist/bin/installer/common.js +25 -0
  13. package/dist/bin/installer/common.js.map +2 -2
  14. package/dist/bin/installer/config-prompt.js +25 -1
  15. package/dist/bin/installer/config-prompt.js.map +2 -2
  16. package/dist/bin/installer/index.js +23 -0
  17. package/dist/bin/installer/index.js.map +2 -2
  18. package/dist/bin/installer/steering.js +5 -1
  19. package/dist/bin/installer/steering.js.map +2 -2
  20. package/dist/bin/kirograph.js +1 -1
  21. package/dist/config.js +63 -2
  22. package/dist/config.js.map +2 -2
  23. package/dist/mcp/handlers/memory.js +17 -5
  24. package/dist/mcp/handlers/memory.js.map +2 -2
  25. package/dist/mcp/handlers/security.js +13 -2
  26. package/dist/mcp/handlers/security.js.map +2 -2
  27. package/dist/mcp/handlers/wiki.js +11 -1
  28. package/dist/mcp/handlers/wiki.js.map +2 -2
  29. package/dist/mcp/tools.js +4 -4
  30. package/dist/mcp/tools.js.map +2 -2
  31. package/dist/memory/index.js +40 -10
  32. package/dist/memory/index.js.map +2 -2
  33. package/dist/memory/relation-display.js +37 -0
  34. package/dist/memory/relation-display.js.map +7 -0
  35. package/dist/patterns/library/sql-injection-concat-js.yaml +3 -0
  36. package/dist/patterns/library/sql-injection-template-js.yaml +4 -0
  37. package/dist/security/attack-surface.js +20 -2
  38. package/dist/security/attack-surface.js.map +2 -2
  39. package/dist/security/data-flows.js +0 -10
  40. package/dist/security/data-flows.js.map +2 -2
  41. package/dist/wiki/index.js +15 -2
  42. package/dist/wiki/index.js.map +2 -2
  43. package/dist/wiki/lint.js +23 -11
  44. package/dist/wiki/lint.js.map +2 -2
  45. package/package.json +1 -1
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/bin/commands/wiki.ts"],
4
- "sourcesContent": ["/**\n * KiroGraph Wiki CLI\n *\n * kirograph wiki init\n * kirograph wiki ingest [source-file]\n * kirograph wiki apply-diff [diff-file]\n * kirograph wiki search <query>\n * kirograph wiki page <slug>\n * kirograph wiki list\n * kirograph wiki lint\n * kirograph wiki links <slug>\n * kirograph wiki rename <from> <to>\n * kirograph wiki reindex\n * kirograph wiki status\n */\n\nimport { Command } from 'commander';\nimport * as fs from 'fs';\nimport { dim, reset, violet, bold, section, green } from '../ui';\n\nconst yellow = '\\x1b[33m';\n\nasync function getWiki(cwd: string) {\n const { KiroGraphWiki } = await Promise.resolve().then(() => require('../../wiki/index.js'));\n const { loadConfig } = await Promise.resolve().then(() => require('../../config.js'));\n const KiroGraph = (await Promise.resolve().then(() => require('../../index.js'))).default;\n\n if (!KiroGraph.isInitialized(cwd)) {\n console.error(' \u2716 KiroGraph is not initialized. Run `kirograph init` first.');\n process.exit(1);\n }\n const config = await loadConfig(cwd);\n if (!config.enableWiki) {\n console.error(' \u2716 Wiki is not enabled. Set enableWiki: true in .kirograph/config.json');\n process.exit(1);\n }\n\n const cg = await KiroGraph.open(cwd);\n const db = cg.getDatabase();\n db.applyWikiSchema();\n\n const kirographDir = `${cwd}/.kirograph`;\n const wiki = new KiroGraphWiki(db.getRawDb(), kirographDir, {\n autoResolveConflicts: config.wikiAutoResolveConflicts,\n typedPages: config.wikiTypedPages,\n });\n wiki.initialize();\n return wiki;\n}\n\nfunction readStdinSync(): string {\n return fs.readFileSync('/dev/stdin', 'utf8');\n}\n\nexport function register(program: Command): void {\n const wiki = program\n .command('wiki')\n .description('LLM-maintained structured wiki (requires enableWiki: true)');\n\n // \u2500\u2500 init \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('init')\n .description('Initialize wiki: create SCHEMA.md and MANIFEST.md in .kirograph/wiki/')\n .action(async () => {\n const { KiroGraphWiki } = await Promise.resolve().then(() => require('../../wiki/index.js'));\n const KiroGraph = (await Promise.resolve().then(() => require('../../index.js'))).default;\n const cwd = process.cwd();\n if (!KiroGraph.isInitialized(cwd)) {\n console.error(' \u2716 KiroGraph is not initialized. Run `kirograph init` first.');\n process.exit(1);\n }\n const { loadConfig } = await Promise.resolve().then(() => require('../../config.js'));\n const config = await loadConfig(cwd);\n const cg = await KiroGraph.open(cwd);\n const db = cg.getDatabase();\n db.applyWikiSchema();\n const w = new KiroGraphWiki(db.getRawDb(), `${cwd}/.kirograph`, {\n autoResolveConflicts: config.wikiAutoResolveConflicts,\n });\n w.initWiki();\n console.log(`\\n ${green}\u2713${reset} Wiki initialized in ${dim}.kirograph/wiki/${reset}`);\n console.log(` ${dim}Edit .kirograph/wiki/SCHEMA.md to customize naming and page structure.${reset}\\n`);\n });\n\n // \u2500\u2500 ingest \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('ingest [source]')\n .description('Print the ingest prompt for the LLM (reads file or stdin)')\n .option('--name <name>', 'Source name to include in the prompt')\n .action(async (source: string | undefined, opts: { name?: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n\n let content: string;\n let sourceName = opts.name ?? source ?? 'source';\n\n if (source && fs.existsSync(source)) {\n content = fs.readFileSync(source, 'utf8');\n sourceName = opts.name ?? source;\n } else if (source) {\n content = source;\n } else {\n content = readStdinSync();\n }\n\n const prompt = w.getIngestPrompt(content, sourceName);\n console.log(`\\n ${section('Wiki Ingest Prompt')} ${dim}(pass to LLM, then run wiki apply-diff)${reset}\\n`);\n console.log(prompt);\n console.log();\n });\n\n // \u2500\u2500 apply-diff \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('apply-diff [diff]')\n .description('Apply a WIKI_DIFF string to the wiki (reads file or stdin)')\n .action(async (diff: string | undefined) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n\n let rawDiff: string;\n if (diff && fs.existsSync(diff)) {\n rawDiff = fs.readFileSync(diff, 'utf8');\n } else if (diff) {\n rawDiff = diff;\n } else {\n rawDiff = readStdinSync();\n }\n\n const result = w.applyDiff(rawDiff);\n\n console.log(`\\n ${green}\u2713${reset} Wiki diff applied\\n`);\n if (result.created.length) {\n console.log(` ${violet}Created:${reset} ${result.created.join(', ')}`);\n }\n if (result.updated.length) {\n console.log(` ${violet}Updated:${reset} ${result.updated.join(', ')}`);\n }\n if (result.conflictsResolved.length) {\n console.log(` ${green}Conflicts resolved:${reset} ${result.conflictsResolved.join(', ')}`);\n }\n if (result.conflictsPending.length) {\n console.log(`\\n ${yellow}\u26A1 Conflicts pending (${result.conflictsPending.length}):${reset}`);\n for (const c of result.conflictsPending) {\n console.log(` ${dim} ${c.page} \u00A7${c.section}${reset}`);\n console.log(` existing: \"${c.existing}\"`);\n console.log(` incoming: \"${c.incoming}\" (source: ${c.source})`);\n }\n }\n console.log();\n });\n\n // \u2500\u2500 search \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('search <query>')\n .description('Full-text search over wiki pages')\n .option('--limit <n>', 'Max results', '5')\n .option('--format <fmt>', 'Output format: text, json', 'text')\n .action(async (query: string, opts: { limit: string; format: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const results = w.search(query, parseInt(opts.limit));\n\n if (opts.format === 'json') {\n console.log(JSON.stringify(results.map(r => ({\n slug: r.page.slug,\n title: r.page.title,\n score: r.score,\n updatedAt: r.page.updatedAt,\n })), null, 2));\n return;\n }\n\n if (results.length === 0) {\n console.log(`\\n ${dim}No wiki pages found for \"${query}\"${reset}\\n`);\n return;\n }\n\n console.log(`\\n ${section('Wiki Search:')} ${violet}${bold}${query}${reset}\\n`);\n for (const { page, score } of results) {\n console.log(` ${violet}[${page.slug}]${reset} ${bold}${page.title}${reset} ${dim}score: ${score.toFixed(3)}${reset}`);\n const preview = page.content.split('\\n').find(l => l.trim() && !l.startsWith('#'));\n if (preview) console.log(` ${dim}${preview.trim().slice(0, 120)}${reset}`);\n console.log();\n }\n });\n\n // \u2500\u2500 page \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('page <slug>')\n .description('Print the full content of a wiki page')\n .action(async (slug: string) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const page = w.getPage(slug);\n if (!page) {\n console.error(` \u2716 Wiki page \"${slug}\" not found. Run \\`kirograph wiki list\\` to see available pages.`);\n process.exit(1);\n }\n console.log();\n console.log(page.content);\n });\n\n // \u2500\u2500 list \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('list')\n .description('List all wiki pages')\n .option('--format <fmt>', 'Output format: text, json', 'text')\n .action(async (opts: { format: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const pages = w.listPages();\n\n if (opts.format === 'json') {\n console.log(JSON.stringify(pages.map(p => ({\n slug: p.slug,\n title: p.title,\n sourceCount: p.sourceCount,\n updatedAt: p.updatedAt,\n })), null, 2));\n return;\n }\n\n const stats = w.getStats();\n console.log(`\\n ${section('Wiki')} ${dim}${stats.pageCount} page(s)${reset}\\n`);\n if (pages.length === 0) {\n console.log(` ${dim}No pages yet. Run \\`kirograph wiki ingest\\` to add pages.${reset}\\n`);\n return;\n }\n for (const p of pages) {\n const date = new Date(p.updatedAt).toISOString().slice(0, 10);\n console.log(` ${violet}${p.slug.padEnd(32)}${reset} ${p.title} ${dim}(${p.sourceCount} src, ${date})${reset}`);\n }\n console.log();\n });\n\n // \u2500\u2500 lint \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('lint')\n .description('Health check the wiki for issues')\n .action(async () => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const issues = w.lint();\n\n if (issues.length === 0) {\n console.log(`\\n ${green}\u2713${reset} Wiki lint passed \u2014 no issues found.\\n`);\n return;\n }\n\n console.log(`\\n ${section('Wiki Lint')} ${yellow}${issues.length} issue(s)${reset}\\n`);\n for (const issue of issues) {\n const icon = issue.kind === 'contradiction' ? '\u26A1' : issue.kind === 'orphan' ? '\u25CB' : issue.kind === 'broken_link' ? '\uD83D\uDD17' : issue.kind === 'schema_error' ? '\u2716' : '\u26A0';\n console.log(` ${icon} ${dim}[${issue.kind}]${reset} ${violet}${issue.slug}${reset}`);\n console.log(` ${issue.detail}`);\n console.log();\n }\n });\n\n // \u2500\u2500 links \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('links <slug>')\n .description('Show outgoing, broken, and incoming [[slug]] links for a page')\n .option('--format <fmt>', 'Output format: text, json', 'text')\n .action(async (slug: string, opts: { format: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const links = w.getLinks(slug);\n\n if (!links) {\n console.error(` \u2716 Wiki page \"${slug}\" not found. Run \\`kirograph wiki list\\` to see available pages.`);\n process.exit(1);\n }\n\n if (opts.format === 'json') {\n console.log(JSON.stringify(links, null, 2));\n return;\n }\n\n console.log(`\\n ${section('Wiki Links:')} ${violet}${bold}${slug}${reset}\\n`);\n\n console.log(` ${bold}Outgoing${reset} ${dim}(${links.outgoing.length})${reset}`);\n if (links.outgoing.length === 0) {\n console.log(` ${dim}(none)${reset}`);\n } else {\n for (const s of links.outgoing) console.log(` ${violet}\u2192${reset} [[${s}]]`);\n }\n\n if (links.broken.length > 0) {\n console.log(`\\n ${yellow}Broken${reset} ${dim}(${links.broken.length})${reset}`);\n for (const s of links.broken) console.log(` ${yellow}\u26A0${reset} [[${s}]] ${dim}\u2014 page does not exist${reset}`);\n }\n\n console.log(`\\n ${bold}Incoming${reset} ${dim}(${links.incoming.length}) \u2014 pages that link here${reset}`);\n if (links.incoming.length === 0) {\n console.log(` ${dim}(none)${reset}`);\n } else {\n for (const s of links.incoming) console.log(` ${violet}\u2190${reset} [[${s}]]`);\n }\n console.log();\n });\n\n // \u2500\u2500 rename \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('rename <from> <to>')\n .description('Rename a page slug, moving its file and updating every [[slug]] reference to it')\n .action(async (from: string, to: string) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n\n let result;\n try {\n result = w.rename(from, to);\n } catch (err) {\n console.error(` \u2716 ${err instanceof Error ? err.message : String(err)}`);\n process.exit(1);\n }\n\n console.log(`\\n ${green}\u2713${reset} Renamed ${violet}[[${result.from}]]${reset} \u2192 ${violet}[[${result.to}]]${reset}\\n`);\n if (result.linksUpdated.length > 0) {\n console.log(` ${bold}Links updated in ${result.linksUpdated.length} page(s):${reset}`);\n for (const s of result.linksUpdated) console.log(` ${dim}\u00B7${reset} ${s}`);\n } else {\n console.log(` ${dim}No other pages referenced [[${result.from}]].${reset}`);\n }\n console.log();\n });\n\n // \u2500\u2500 reindex \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('reindex')\n .description('Rebuild SQLite index from .kirograph/wiki/*.md files')\n .action(async () => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const count = w.reindex();\n console.log(`\\n ${green}\u2713${reset} Reindexed ${bold}${count}${reset} wiki page(s)\\n`);\n });\n\n // \u2500\u2500 status \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('status')\n .description('Wiki subsystem stats')\n .action(async () => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const stats = w.getStats();\n const oldest = stats.oldestPage ? new Date(stats.oldestPage).toISOString().slice(0, 10) : 'n/a';\n const newest = stats.newestPage ? new Date(stats.newestPage).toISOString().slice(0, 10) : 'n/a';\n console.log(`\\n ${section('Wiki Status')}\\n`);\n console.log(` Pages: ${bold}${stats.pageCount}${reset}`);\n console.log(` Total sources: ${bold}${stats.totalSources}${reset}`);\n console.log(` Oldest page: ${dim}${oldest}${reset}`);\n console.log(` Newest page: ${dim}${newest}${reset}`);\n console.log(` Wiki dir: ${dim}.kirograph/wiki/${reset}\\n`);\n });\n\n // \u2500\u2500 synthesize (local model) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('synthesize')\n .description('Run local-model wiki synthesis: process the pending source queue (wikiSynthesisMode: local)')\n .option('--quiet', 'suppress progress output')\n .action(async (opts) => {\n const { KiroGraphWiki } = await Promise.resolve().then(() => require('../../wiki/index.js'));\n const { loadConfig } = await Promise.resolve().then(() => require('../../config.js'));\n const KiroGraph = (await Promise.resolve().then(() => require('../../index.js'))).default;\n const cwd = process.cwd();\n\n if (!KiroGraph.isInitialized(cwd)) {\n console.error(' \u2716 KiroGraph is not initialized. Run `kirograph init` first.');\n process.exit(1);\n }\n const config = await loadConfig(cwd);\n if (!config.enableWiki) {\n console.error(' \u2716 Wiki is not enabled.');\n process.exit(1);\n }\n if (config.wikiSynthesisMode !== 'local') {\n console.error(' \u2716 wikiSynthesisMode is not \"local\". This command is for local-model synthesis only.');\n process.exit(1);\n }\n\n const cg = await KiroGraph.open(cwd);\n const db = cg.getDatabase();\n db.applyWikiSchema();\n const w = new KiroGraphWiki(db.getRawDb(), `${cwd}/.kirograph`, {\n autoResolveConflicts: config.wikiAutoResolveConflicts,\n });\n w.initialize();\n\n const queueCount = w.getQueueCount();\n if (queueCount === 0) {\n if (!opts.quiet) console.log(`\\n ${dim}Wiki queue is empty \u2014 nothing to synthesize.${reset}\\n`);\n process.exit(0);\n }\n\n if (!opts.quiet) console.log(`\\n ${yellow}\u27F3${reset} Synthesizing ${bold}${queueCount}${reset} queued source(s) with local model...\\n`);\n\n const result = await w.synthesize(config.wikiLocalModel, !!opts.quiet);\n\n if (!opts.quiet) {\n if (result.processed > 0) {\n console.log(` ${green}\u2713${reset} Processed: ${bold}${result.processed}${reset} source(s)`);\n if (result.created.length) console.log(` ${green}\u2713${reset} Created: ${result.created.join(', ')}`);\n if (result.updated.length) console.log(` ${green}\u2713${reset} Updated: ${result.updated.join(', ')}`);\n }\n if (result.errors.length) {\n for (const e of result.errors) console.error(` ${yellow}\u26A0${reset} ${e}`);\n }\n console.log('');\n }\n });\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["/**\n * KiroGraph Wiki CLI\n *\n * kirograph wiki init\n * kirograph wiki ingest [source-file]\n * kirograph wiki apply-diff [diff-file]\n * kirograph wiki search <query>\n * kirograph wiki page <slug>\n * kirograph wiki list\n * kirograph wiki lint\n * kirograph wiki links <slug>\n * kirograph wiki rename <from> <to>\n * kirograph wiki reindex\n * kirograph wiki status\n */\n\nimport { Command } from 'commander';\nimport * as fs from 'fs';\nimport { dim, reset, violet, bold, section, green } from '../ui';\n\nconst yellow = '\\x1b[33m';\n\nasync function getWiki(cwd: string) {\n const { KiroGraphWiki } = await Promise.resolve().then(() => require('../../wiki/index.js'));\n const { loadConfig } = await Promise.resolve().then(() => require('../../config.js'));\n const KiroGraph = (await Promise.resolve().then(() => require('../../index.js'))).default;\n\n if (!KiroGraph.isInitialized(cwd)) {\n console.error(' \u2716 KiroGraph is not initialized. Run `kirograph init` first.');\n process.exit(1);\n }\n const config = await loadConfig(cwd);\n if (!config.enableWiki) {\n console.error(' \u2716 Wiki is not enabled. Set enableWiki: true in .kirograph/config.json');\n process.exit(1);\n }\n\n const cg = await KiroGraph.open(cwd);\n const db = cg.getDatabase();\n db.applyWikiSchema();\n\n const kirographDir = `${cwd}/.kirograph`;\n const wiki = new KiroGraphWiki(db.getRawDb(), kirographDir, {\n autoResolveConflicts: config.wikiAutoResolveConflicts,\n wikiContradictionMode: config.wikiContradictionMode,\n wikiContradictionConfidenceThreshold: config.wikiContradictionConfidenceThreshold,\n jevApiKey: config.jevApiKey,\n jevBaseUrl: config.jevBaseUrl,\n jevModel: config.jevModel,\n typedPages: config.wikiTypedPages,\n });\n wiki.initialize();\n return wiki;\n}\n\nfunction readStdinSync(): string {\n return fs.readFileSync('/dev/stdin', 'utf8');\n}\n\nexport function register(program: Command): void {\n const wiki = program\n .command('wiki')\n .description('LLM-maintained structured wiki (requires enableWiki: true)');\n\n // \u2500\u2500 init \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('init')\n .description('Initialize wiki: create SCHEMA.md and MANIFEST.md in .kirograph/wiki/')\n .action(async () => {\n const { KiroGraphWiki } = await Promise.resolve().then(() => require('../../wiki/index.js'));\n const KiroGraph = (await Promise.resolve().then(() => require('../../index.js'))).default;\n const cwd = process.cwd();\n if (!KiroGraph.isInitialized(cwd)) {\n console.error(' \u2716 KiroGraph is not initialized. Run `kirograph init` first.');\n process.exit(1);\n }\n const { loadConfig } = await Promise.resolve().then(() => require('../../config.js'));\n const config = await loadConfig(cwd);\n const cg = await KiroGraph.open(cwd);\n const db = cg.getDatabase();\n db.applyWikiSchema();\n const w = new KiroGraphWiki(db.getRawDb(), `${cwd}/.kirograph`, {\n autoResolveConflicts: config.wikiAutoResolveConflicts,\n });\n w.initWiki();\n console.log(`\\n ${green}\u2713${reset} Wiki initialized in ${dim}.kirograph/wiki/${reset}`);\n console.log(` ${dim}Edit .kirograph/wiki/SCHEMA.md to customize naming and page structure.${reset}\\n`);\n });\n\n // \u2500\u2500 ingest \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('ingest [source]')\n .description('Print the ingest prompt for the LLM (reads file or stdin)')\n .option('--name <name>', 'Source name to include in the prompt')\n .action(async (source: string | undefined, opts: { name?: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n\n let content: string;\n let sourceName = opts.name ?? source ?? 'source';\n\n if (source && fs.existsSync(source)) {\n content = fs.readFileSync(source, 'utf8');\n sourceName = opts.name ?? source;\n } else if (source) {\n content = source;\n } else {\n content = readStdinSync();\n }\n\n const prompt = w.getIngestPrompt(content, sourceName);\n console.log(`\\n ${section('Wiki Ingest Prompt')} ${dim}(pass to LLM, then run wiki apply-diff)${reset}\\n`);\n console.log(prompt);\n console.log();\n });\n\n // \u2500\u2500 apply-diff \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('apply-diff [diff]')\n .description('Apply a WIKI_DIFF string to the wiki (reads file or stdin)')\n .action(async (diff: string | undefined) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n\n let rawDiff: string;\n if (diff && fs.existsSync(diff)) {\n rawDiff = fs.readFileSync(diff, 'utf8');\n } else if (diff) {\n rawDiff = diff;\n } else {\n rawDiff = readStdinSync();\n }\n\n const result = w.applyDiff(rawDiff);\n\n console.log(`\\n ${green}\u2713${reset} Wiki diff applied\\n`);\n if (result.created.length) {\n console.log(` ${violet}Created:${reset} ${result.created.join(', ')}`);\n }\n if (result.updated.length) {\n console.log(` ${violet}Updated:${reset} ${result.updated.join(', ')}`);\n }\n if (result.conflictsResolved.length) {\n console.log(` ${green}Conflicts resolved:${reset} ${result.conflictsResolved.join(', ')}`);\n }\n if (result.conflictsPending.length) {\n console.log(`\\n ${yellow}\u26A1 Conflicts pending (${result.conflictsPending.length}):${reset}`);\n for (const c of result.conflictsPending) {\n console.log(` ${dim} ${c.page} \u00A7${c.section}${reset}`);\n console.log(` existing: \"${c.existing}\"`);\n console.log(` incoming: \"${c.incoming}\" (source: ${c.source})`);\n }\n }\n console.log();\n });\n\n // \u2500\u2500 search \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('search <query>')\n .description('Full-text search over wiki pages')\n .option('--limit <n>', 'Max results', '5')\n .option('--format <fmt>', 'Output format: text, json', 'text')\n .action(async (query: string, opts: { limit: string; format: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const results = w.search(query, parseInt(opts.limit));\n\n if (opts.format === 'json') {\n console.log(JSON.stringify(results.map(r => ({\n slug: r.page.slug,\n title: r.page.title,\n score: r.score,\n updatedAt: r.page.updatedAt,\n })), null, 2));\n return;\n }\n\n if (results.length === 0) {\n console.log(`\\n ${dim}No wiki pages found for \"${query}\"${reset}\\n`);\n return;\n }\n\n console.log(`\\n ${section('Wiki Search:')} ${violet}${bold}${query}${reset}\\n`);\n for (const { page, score } of results) {\n console.log(` ${violet}[${page.slug}]${reset} ${bold}${page.title}${reset} ${dim}score: ${score.toFixed(3)}${reset}`);\n const preview = page.content.split('\\n').find(l => l.trim() && !l.startsWith('#'));\n if (preview) console.log(` ${dim}${preview.trim().slice(0, 120)}${reset}`);\n console.log();\n }\n });\n\n // \u2500\u2500 page \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('page <slug>')\n .description('Print the full content of a wiki page')\n .action(async (slug: string) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const page = w.getPage(slug);\n if (!page) {\n console.error(` \u2716 Wiki page \"${slug}\" not found. Run \\`kirograph wiki list\\` to see available pages.`);\n process.exit(1);\n }\n console.log();\n console.log(page.content);\n });\n\n // \u2500\u2500 list \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('list')\n .description('List all wiki pages')\n .option('--format <fmt>', 'Output format: text, json', 'text')\n .action(async (opts: { format: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const pages = w.listPages();\n\n if (opts.format === 'json') {\n console.log(JSON.stringify(pages.map(p => ({\n slug: p.slug,\n title: p.title,\n sourceCount: p.sourceCount,\n updatedAt: p.updatedAt,\n })), null, 2));\n return;\n }\n\n const stats = w.getStats();\n console.log(`\\n ${section('Wiki')} ${dim}${stats.pageCount} page(s)${reset}\\n`);\n if (pages.length === 0) {\n console.log(` ${dim}No pages yet. Run \\`kirograph wiki ingest\\` to add pages.${reset}\\n`);\n return;\n }\n for (const p of pages) {\n const date = new Date(p.updatedAt).toISOString().slice(0, 10);\n console.log(` ${violet}${p.slug.padEnd(32)}${reset} ${p.title} ${dim}(${p.sourceCount} src, ${date})${reset}`);\n }\n console.log();\n });\n\n // \u2500\u2500 lint \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('lint')\n .description('Health check the wiki for issues')\n .action(async () => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n let issues;\n try {\n issues = await w.lint();\n } catch (err) {\n console.error(` \u2716 ${err instanceof Error ? err.message : String(err)}`);\n process.exit(1);\n }\n\n if (issues.length === 0) {\n console.log(`\\n ${green}\u2713${reset} Wiki lint passed \u2014 no issues found.\\n`);\n return;\n }\n\n console.log(`\\n ${section('Wiki Lint')} ${yellow}${issues.length} issue(s)${reset}\\n`);\n for (const issue of issues) {\n const icon = issue.kind === 'contradiction' ? '\u26A1' : issue.kind === 'orphan' ? '\u25CB' : issue.kind === 'broken_link' ? '\uD83D\uDD17' : issue.kind === 'schema_error' ? '\u2716' : '\u26A0';\n console.log(` ${icon} ${dim}[${issue.kind}]${reset} ${violet}${issue.slug}${reset}`);\n console.log(` ${issue.detail}`);\n console.log();\n }\n });\n\n // \u2500\u2500 links \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('links <slug>')\n .description('Show outgoing, broken, and incoming [[slug]] links for a page')\n .option('--format <fmt>', 'Output format: text, json', 'text')\n .action(async (slug: string, opts: { format: string }) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const links = w.getLinks(slug);\n\n if (!links) {\n console.error(` \u2716 Wiki page \"${slug}\" not found. Run \\`kirograph wiki list\\` to see available pages.`);\n process.exit(1);\n }\n\n if (opts.format === 'json') {\n console.log(JSON.stringify(links, null, 2));\n return;\n }\n\n console.log(`\\n ${section('Wiki Links:')} ${violet}${bold}${slug}${reset}\\n`);\n\n console.log(` ${bold}Outgoing${reset} ${dim}(${links.outgoing.length})${reset}`);\n if (links.outgoing.length === 0) {\n console.log(` ${dim}(none)${reset}`);\n } else {\n for (const s of links.outgoing) console.log(` ${violet}\u2192${reset} [[${s}]]`);\n }\n\n if (links.broken.length > 0) {\n console.log(`\\n ${yellow}Broken${reset} ${dim}(${links.broken.length})${reset}`);\n for (const s of links.broken) console.log(` ${yellow}\u26A0${reset} [[${s}]] ${dim}\u2014 page does not exist${reset}`);\n }\n\n console.log(`\\n ${bold}Incoming${reset} ${dim}(${links.incoming.length}) \u2014 pages that link here${reset}`);\n if (links.incoming.length === 0) {\n console.log(` ${dim}(none)${reset}`);\n } else {\n for (const s of links.incoming) console.log(` ${violet}\u2190${reset} [[${s}]]`);\n }\n console.log();\n });\n\n // \u2500\u2500 rename \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('rename <from> <to>')\n .description('Rename a page slug, moving its file and updating every [[slug]] reference to it')\n .action(async (from: string, to: string) => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n\n let result;\n try {\n result = w.rename(from, to);\n } catch (err) {\n console.error(` \u2716 ${err instanceof Error ? err.message : String(err)}`);\n process.exit(1);\n }\n\n console.log(`\\n ${green}\u2713${reset} Renamed ${violet}[[${result.from}]]${reset} \u2192 ${violet}[[${result.to}]]${reset}\\n`);\n if (result.linksUpdated.length > 0) {\n console.log(` ${bold}Links updated in ${result.linksUpdated.length} page(s):${reset}`);\n for (const s of result.linksUpdated) console.log(` ${dim}\u00B7${reset} ${s}`);\n } else {\n console.log(` ${dim}No other pages referenced [[${result.from}]].${reset}`);\n }\n console.log();\n });\n\n // \u2500\u2500 reindex \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('reindex')\n .description('Rebuild SQLite index from .kirograph/wiki/*.md files')\n .action(async () => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const count = w.reindex();\n console.log(`\\n ${green}\u2713${reset} Reindexed ${bold}${count}${reset} wiki page(s)\\n`);\n });\n\n // \u2500\u2500 status \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('status')\n .description('Wiki subsystem stats')\n .action(async () => {\n const cwd = process.cwd();\n const w = await getWiki(cwd);\n const stats = w.getStats();\n const oldest = stats.oldestPage ? new Date(stats.oldestPage).toISOString().slice(0, 10) : 'n/a';\n const newest = stats.newestPage ? new Date(stats.newestPage).toISOString().slice(0, 10) : 'n/a';\n console.log(`\\n ${section('Wiki Status')}\\n`);\n console.log(` Pages: ${bold}${stats.pageCount}${reset}`);\n console.log(` Total sources: ${bold}${stats.totalSources}${reset}`);\n console.log(` Oldest page: ${dim}${oldest}${reset}`);\n console.log(` Newest page: ${dim}${newest}${reset}`);\n console.log(` Wiki dir: ${dim}.kirograph/wiki/${reset}\\n`);\n });\n\n // \u2500\u2500 synthesize (local model) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n wiki\n .command('synthesize')\n .description('Run local-model wiki synthesis: process the pending source queue (wikiSynthesisMode: local)')\n .option('--quiet', 'suppress progress output')\n .action(async (opts) => {\n const { KiroGraphWiki } = await Promise.resolve().then(() => require('../../wiki/index.js'));\n const { loadConfig } = await Promise.resolve().then(() => require('../../config.js'));\n const KiroGraph = (await Promise.resolve().then(() => require('../../index.js'))).default;\n const cwd = process.cwd();\n\n if (!KiroGraph.isInitialized(cwd)) {\n console.error(' \u2716 KiroGraph is not initialized. Run `kirograph init` first.');\n process.exit(1);\n }\n const config = await loadConfig(cwd);\n if (!config.enableWiki) {\n console.error(' \u2716 Wiki is not enabled.');\n process.exit(1);\n }\n if (config.wikiSynthesisMode !== 'local') {\n console.error(' \u2716 wikiSynthesisMode is not \"local\". This command is for local-model synthesis only.');\n process.exit(1);\n }\n\n const cg = await KiroGraph.open(cwd);\n const db = cg.getDatabase();\n db.applyWikiSchema();\n const w = new KiroGraphWiki(db.getRawDb(), `${cwd}/.kirograph`, {\n autoResolveConflicts: config.wikiAutoResolveConflicts,\n });\n w.initialize();\n\n const queueCount = w.getQueueCount();\n if (queueCount === 0) {\n if (!opts.quiet) console.log(`\\n ${dim}Wiki queue is empty \u2014 nothing to synthesize.${reset}\\n`);\n process.exit(0);\n }\n\n if (!opts.quiet) console.log(`\\n ${yellow}\u27F3${reset} Synthesizing ${bold}${queueCount}${reset} queued source(s) with local model...\\n`);\n\n const result = await w.synthesize(config.wikiLocalModel, !!opts.quiet);\n\n if (!opts.quiet) {\n if (result.processed > 0) {\n console.log(` ${green}\u2713${reset} Processed: ${bold}${result.processed}${reset} source(s)`);\n if (result.created.length) console.log(` ${green}\u2713${reset} Created: ${result.created.join(', ')}`);\n if (result.updated.length) console.log(` ${green}\u2713${reset} Updated: ${result.updated.join(', ')}`);\n }\n if (result.errors.length) {\n for (const e of result.errors) console.error(` ${yellow}\u26A0${reset} ${e}`);\n }\n console.log('');\n }\n });\n}\n"],
5
+ "mappings": "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",
6
6
  "names": []
7
7
  }
@@ -37,6 +37,7 @@ __export(common_exports, {
37
37
  appendImportLine: () => appendImportLine,
38
38
  buildInstructionOpts: () => buildInstructionOpts,
39
39
  ensureDir: () => ensureDir,
40
+ ensureJevEnvFile: () => ensureJevEnvFile,
40
41
  overwriteMcpServersConfig: () => overwriteMcpServersConfig,
41
42
  printMcpCommand: () => printMcpCommand,
42
43
  printMcpSetup: () => printMcpSetup,
@@ -66,6 +67,29 @@ const KIROGRAPH_SCOPED_TOOLS = import_tool_names.KIROGRAPH_TOOL_NAMES.map((name)
66
67
  function ensureDir(p) {
67
68
  fs.mkdirSync(p, { recursive: true });
68
69
  }
70
+ function ensureJevEnvFile(projectRoot) {
71
+ const kirographDir = path.join(projectRoot, ".kirograph");
72
+ const envPath = path.join(kirographDir, ".env");
73
+ if (fs.existsSync(envPath)) return false;
74
+ ensureDir(kirographDir);
75
+ fs.writeFileSync(envPath, [
76
+ "# KiroGraph \u2014 jev (TypeSafe System One) API key",
77
+ "# Used by memoryRelationMode / wikiContradictionMode / securityAuthDetectionMode: 'jev'",
78
+ "# Get a key at https://docs.typesafe.ai \u2014 this file should never be committed to git.",
79
+ "JEV_API_KEY=",
80
+ ""
81
+ ].join("\n"));
82
+ const gitignorePath = path.join(projectRoot, ".gitignore");
83
+ if (fs.existsSync(gitignorePath)) {
84
+ const content = fs.readFileSync(gitignorePath, "utf8");
85
+ if (!content.includes(".kirograph/.env")) {
86
+ const sep = content.length === 0 || content.endsWith("\n") ? "" : "\n";
87
+ fs.appendFileSync(gitignorePath, `${sep}.kirograph/.env
88
+ `);
89
+ }
90
+ }
91
+ return true;
92
+ }
69
93
  function readJson(p) {
70
94
  try {
71
95
  return JSON.parse(fs.readFileSync(p, "utf8"));
@@ -212,6 +236,7 @@ function printMcpCommand(command) {
212
236
  appendImportLine,
213
237
  buildInstructionOpts,
214
238
  ensureDir,
239
+ ensureJevEnvFile,
215
240
  overwriteMcpServersConfig,
216
241
  printMcpCommand,
217
242
  printMcpSetup,
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/bin/installer/common.ts"],
4
- "sourcesContent": ["import * as fs from 'fs';\nimport * as path from 'path';\nimport { KIROGRAPH_TOOL_NAMES } from '../../mcp/tool-names';\nimport type { InstructionOptions } from './instructions';\nimport type { CavemanMode } from './caveman';\n\n/** Single options object passed to every target's installLate(). */\nexport interface LateInstallOptions {\n cavemanMode?: CavemanMode | 'off';\n shellCompressionLevel?: string;\n enableMemory?: boolean;\n enableDocs?: boolean;\n enableData?: boolean;\n enableSecurity?: boolean;\n enableArchitecture?: boolean;\n enablePatterns?: boolean;\n enableWatchmen?: boolean;\n watchmenSynthesisMode?: 'local' | 'agent';\n enableWiki?: boolean;\n wikiSynthesisMode?: 'local' | 'agent';\n wikiLocalModel?: string;\n enableCodeHealth?: boolean;\n enableNavigation?: boolean;\n enableComplexity?: boolean;\n enableGitContext?: boolean;\n enableEditPrimitives?: boolean;\n enableBranch?: boolean;\n enableAgentUtils?: boolean;\n enableGeneralCompression?: boolean;\n trackCallSites?: boolean;\n kiroHookFormat?: 'v1-legacy' | 'v2';\n}\n\nexport type InstallTarget = 'kiro' | 'claude' | 'codex' | 'cursor' | 'antigravity' | 'opencode' | 'windsurf' | 'cline' | 'copilot' | 'copilot-cli' | 'junie' | 'gemini-cli' | 'continue' | 'roo' | 'warp' | 'aider' | 'trae' | 'augment' | 'kilo' | 'amp' | 'devin' | 'replit' | 'goose' | 'openhands' | 'tabnine' | 'mistral-vibe' | 'ibm-bob' | 'crush' | 'droid-factory' | 'forgecode' | 'iflow' | 'qwen' | 'rovo' | 'qoder' | 'commandcode';\n\nexport const KIROGRAPH_SERVER_NAME = 'kirograph';\nexport const KIROGRAPH_COMMAND = 'kirograph';\nexport const KIROGRAPH_MCP_ARGS = ['serve', '--mcp'];\n\n/**\n * Wrap a kirograph command so it runs quietly and never fails the host process,\n * emitting shell syntax appropriate for the OS the install is running on.\n *\n * Hook commands are executed by the host agent's shell: POSIX sh/bash on\n * macOS/Linux, cmd.exe on Windows. The two use incompatible syntax for\n * discarding output and swallowing a non-zero exit code:\n * - POSIX: `<cmd> >/dev/null 2>&1 || true`\n * - cmd.exe: `<cmd> >nul 2>&1 || exit /b 0`\n *\n * On Windows `/dev/null` is treated as a literal path and `true` is not a valid\n * command, so the bash form silently breaks hooks (see issue #40).\n *\n * @param baseCommand the kirograph invocation without redirection, e.g. `kirograph sync --quiet`\n */\nexport function silentCommand(baseCommand: string): string {\n const isWindows = process.platform === 'win32';\n return isWindows\n ? `${baseCommand} >nul 2>&1 || exit /b 0`\n : `${baseCommand} >/dev/null 2>&1 || true`;\n}\n\nexport const KIROGRAPH_SYNC_CMD = silentCommand('kirograph sync-if-dirty --quiet');\nexport const KIROGRAPH_TOOLS = KIROGRAPH_TOOL_NAMES;\nexport const KIROGRAPH_SCOPED_TOOLS = KIROGRAPH_TOOL_NAMES.map(name => `@kirograph/${name}`);\n\nexport function ensureDir(p: string): void {\n fs.mkdirSync(p, { recursive: true });\n}\n\nexport function readJson(p: string): any {\n try { return JSON.parse(fs.readFileSync(p, 'utf8')); } catch { return {}; }\n}\n\nexport function writeJson(p: string, data: unknown): void {\n fs.writeFileSync(p, JSON.stringify(data, null, 2) + '\\n');\n}\n\n/**\n * Write MCP server config to a JSON file under the mcpServers key.\n * Returns true if the config was written, false if already configured (idempotent).\n */\nexport function writeMcpServersConfig(configPath: string, serverConfig: object): boolean {\n ensureDir(path.dirname(configPath));\n const existing = readJson(configPath);\n existing.mcpServers = existing.mcpServers ?? {};\n if (existing.mcpServers[KIROGRAPH_SERVER_NAME]) {\n return false; // Already configured\n }\n existing.mcpServers[KIROGRAPH_SERVER_NAME] = serverConfig;\n writeJson(configPath, existing);\n return true;\n}\n\n/**\n * Always write (overwrite) the MCP server config entry, regardless of whether it already exists.\n * Used when the final state is known upfront and idempotency would cause stale data.\n */\nexport function overwriteMcpServersConfig(configPath: string, serverConfig: object): void {\n ensureDir(path.dirname(configPath));\n const existing = readJson(configPath);\n existing.mcpServers = existing.mcpServers ?? {};\n existing.mcpServers[KIROGRAPH_SERVER_NAME] = serverConfig;\n writeJson(configPath, existing);\n}\n\nexport function removeMcpServersConfig(configPath: string): boolean {\n if (!fs.existsSync(configPath)) return false;\n const existing = readJson(configPath);\n if (!existing.mcpServers?.[KIROGRAPH_SERVER_NAME]) return false;\n delete existing.mcpServers[KIROGRAPH_SERVER_NAME];\n writeJson(configPath, existing);\n return true;\n}\n\nexport function appendImportLine(filePath: string, line: string, heading: string): boolean {\n const existing = fs.existsSync(filePath) ? fs.readFileSync(filePath, 'utf8') : '';\n if (existing.includes(line)) return false;\n\n const prefix = existing.length > 0 && !existing.endsWith('\\n') ? '\\n' : '';\n const separator = existing.trim().length > 0 ? '\\n' : '';\n fs.writeFileSync(filePath, existing + prefix + separator + heading + '\\n' + line + '\\n');\n return true;\n}\n\nexport function removeImportLine(filePath: string, line: string): boolean {\n if (!fs.existsSync(filePath)) return false;\n const original = fs.readFileSync(filePath, 'utf8');\n const next = original\n .split('\\n')\n .filter(l => l.trim() !== line)\n .join('\\n')\n .replace(/\\n{3,}/g, '\\n\\n');\n if (next === original) return false;\n fs.writeFileSync(filePath, next.endsWith('\\n') ? next : next + '\\n');\n return true;\n}\n\nexport function upsertGeneratedBlock(filePath: string, blockId: string, heading: string, content: string): boolean {\n const start = `<!-- kirograph:${blockId}:start -->`;\n const end = `<!-- kirograph:${blockId}:end -->`;\n const block = `${start}\\n${heading}\\n\\n${content.trim()}\\n${end}`;\n const existing = fs.existsSync(filePath) ? fs.readFileSync(filePath, 'utf8') : '';\n const pattern = new RegExp(`${escapeRegExp(start)}[\\\\s\\\\S]*?${escapeRegExp(end)}`);\n\n if (pattern.test(existing)) {\n const next = existing.replace(pattern, block);\n if (next === existing) return false;\n fs.writeFileSync(filePath, next.endsWith('\\n') ? next : next + '\\n');\n return true;\n }\n\n const prefix = existing.length > 0 && !existing.endsWith('\\n') ? '\\n' : '';\n const separator = existing.trim().length > 0 ? '\\n' : '';\n fs.writeFileSync(filePath, existing + prefix + separator + block + '\\n');\n return true;\n}\n\nexport function removeGeneratedBlock(filePath: string, blockId: string): boolean {\n if (!fs.existsSync(filePath)) return false;\n const start = `<!-- kirograph:${blockId}:start -->`;\n const end = `<!-- kirograph:${blockId}:end -->`;\n const original = fs.readFileSync(filePath, 'utf8');\n const pattern = new RegExp(`\\\\n?${escapeRegExp(start)}[\\\\s\\\\S]*?${escapeRegExp(end)}\\\\n?`);\n const next = original.replace(pattern, '\\n').replace(/\\n{3,}/g, '\\n\\n');\n if (next === original) return false;\n fs.writeFileSync(filePath, next.endsWith('\\n') ? next : next + '\\n');\n return true;\n}\n\nfunction escapeRegExp(s: string): string {\n return s.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\$&');\n}\n\n/**\n * Build InstructionOptions from the installLate parameters.\n * Used by all targets to pass full feature config to buildAgentInstructions.\n */\nexport function buildInstructionOpts(opts: LateInstallOptions, hasHooks?: boolean): InstructionOptions {\n return {\n cavemanMode: opts.cavemanMode,\n shellCompressionLevel: (opts.shellCompressionLevel as InstructionOptions['shellCompressionLevel']) ?? undefined,\n enableArchitecture: opts.enableArchitecture ?? false,\n enableMemory: opts.enableMemory ?? false,\n enableDocs: opts.enableDocs ?? false,\n enableData: opts.enableData ?? false,\n enableSecurity: opts.enableSecurity ?? false,\n enablePatterns: opts.enablePatterns ?? false,\n enableWiki: opts.enableWiki ?? false,\n enableCodeHealth: opts.enableCodeHealth ?? false,\n enableNavigation: opts.enableNavigation ?? false,\n enableComplexity: opts.enableComplexity ?? false,\n enableGitContext: opts.enableGitContext ?? false,\n enableEditPrimitives: opts.enableEditPrimitives ?? false,\n enableBranch: opts.enableBranch ?? false,\n enableAgentUtils: opts.enableAgentUtils ?? false,\n enableGeneralCompression: opts.enableGeneralCompression ?? false,\n trackCallSites: opts.trackCallSites ?? false,\n hasHooks: hasHooks ?? false,\n };\n}\n\nconst violet = '\\x1b[38;5;99m';\nconst resetAnsi = '\\x1b[0m';\nconst dimAnsi = '\\x1b[2m';\nconst boldAnsi = '\\x1b[1m';\n\n/**\n * Print a highlighted MCP config JSON block for targets that need user-scoped setup.\n */\nexport function printMcpSetup(configPath: string, projectRoot: string): void {\n const escapedPath = projectRoot.replace(/\\\\/g, '\\\\\\\\').replace(/\"/g, '\\\\\"');\n console.log(`\\n ${dimAnsi}Add the MCP server manually:${resetAnsi}`);\n console.log(` ${dimAnsi}Edit${resetAnsi} ${violet}${boldAnsi}${configPath}${resetAnsi} ${dimAnsi}and add:${resetAnsi}`);\n console.log(` ${violet}{${resetAnsi}`);\n console.log(` ${violet} \"mcpServers\": {${resetAnsi}`);\n console.log(` ${violet} \"kirograph\": {${resetAnsi}`);\n console.log(` ${violet} \"command\": \"kirograph\",${resetAnsi}`);\n console.log(` ${violet} \"args\": [\"serve\", \"--mcp\", \"--path\", \"${escapedPath}\"]${resetAnsi}`);\n console.log(` ${violet} }${resetAnsi}`);\n console.log(` ${violet} }${resetAnsi}`);\n console.log(` ${violet}}${resetAnsi}\\n`);\n}\n\n/**\n * Print a highlighted CLI command for MCP registration.\n */\nexport function printMcpCommand(command: string): void {\n console.log(`\\n ${dimAnsi}Add the MCP server with:${resetAnsi}`);\n console.log(` ${violet}${boldAnsi}${command}${resetAnsi}\\n`);\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import * as fs from 'fs';\nimport * as path from 'path';\nimport { KIROGRAPH_TOOL_NAMES } from '../../mcp/tool-names';\nimport type { InstructionOptions } from './instructions';\nimport type { CavemanMode } from './caveman';\n\n/** Single options object passed to every target's installLate(). */\nexport interface LateInstallOptions {\n cavemanMode?: CavemanMode | 'off';\n shellCompressionLevel?: string;\n enableMemory?: boolean;\n enableDocs?: boolean;\n enableData?: boolean;\n enableSecurity?: boolean;\n enableArchitecture?: boolean;\n enablePatterns?: boolean;\n enableWatchmen?: boolean;\n watchmenSynthesisMode?: 'local' | 'agent';\n enableWiki?: boolean;\n wikiSynthesisMode?: 'local' | 'agent';\n wikiLocalModel?: string;\n enableCodeHealth?: boolean;\n enableNavigation?: boolean;\n enableComplexity?: boolean;\n enableGitContext?: boolean;\n enableEditPrimitives?: boolean;\n enableBranch?: boolean;\n enableAgentUtils?: boolean;\n enableGeneralCompression?: boolean;\n trackCallSites?: boolean;\n kiroHookFormat?: 'v1-legacy' | 'v2';\n}\n\nexport type InstallTarget = 'kiro' | 'claude' | 'codex' | 'cursor' | 'antigravity' | 'opencode' | 'windsurf' | 'cline' | 'copilot' | 'copilot-cli' | 'junie' | 'gemini-cli' | 'continue' | 'roo' | 'warp' | 'aider' | 'trae' | 'augment' | 'kilo' | 'amp' | 'devin' | 'replit' | 'goose' | 'openhands' | 'tabnine' | 'mistral-vibe' | 'ibm-bob' | 'crush' | 'droid-factory' | 'forgecode' | 'iflow' | 'qwen' | 'rovo' | 'qoder' | 'commandcode';\n\nexport const KIROGRAPH_SERVER_NAME = 'kirograph';\nexport const KIROGRAPH_COMMAND = 'kirograph';\nexport const KIROGRAPH_MCP_ARGS = ['serve', '--mcp'];\n\n/**\n * Wrap a kirograph command so it runs quietly and never fails the host process,\n * emitting shell syntax appropriate for the OS the install is running on.\n *\n * Hook commands are executed by the host agent's shell: POSIX sh/bash on\n * macOS/Linux, cmd.exe on Windows. The two use incompatible syntax for\n * discarding output and swallowing a non-zero exit code:\n * - POSIX: `<cmd> >/dev/null 2>&1 || true`\n * - cmd.exe: `<cmd> >nul 2>&1 || exit /b 0`\n *\n * On Windows `/dev/null` is treated as a literal path and `true` is not a valid\n * command, so the bash form silently breaks hooks (see issue #40).\n *\n * @param baseCommand the kirograph invocation without redirection, e.g. `kirograph sync --quiet`\n */\nexport function silentCommand(baseCommand: string): string {\n const isWindows = process.platform === 'win32';\n return isWindows\n ? `${baseCommand} >nul 2>&1 || exit /b 0`\n : `${baseCommand} >/dev/null 2>&1 || true`;\n}\n\nexport const KIROGRAPH_SYNC_CMD = silentCommand('kirograph sync-if-dirty --quiet');\nexport const KIROGRAPH_TOOLS = KIROGRAPH_TOOL_NAMES;\nexport const KIROGRAPH_SCOPED_TOOLS = KIROGRAPH_TOOL_NAMES.map(name => `@kirograph/${name}`);\n\nexport function ensureDir(p: string): void {\n fs.mkdirSync(p, { recursive: true });\n}\n\n/**\n * Create `.kirograph/.env` with a JEV_API_KEY placeholder when jev-powered\n * classification was enabled during install \u2014 `loadConfig()` reads it into\n * process.env on every command (see `loadDotEnv()` in src/config.ts). Never\n * overwrites an existing `.env` (a re-run of the installer, or a key the\n * user already set, is left alone). Best-effort: also appends the file to\n * an existing project `.gitignore` so the key is never committed, but never\n * creates a `.gitignore` from scratch \u2014 that's outside what installing\n * KiroGraph should do to a project that doesn't already have one.\n * Returns true when a new `.env` file was written.\n */\nexport function ensureJevEnvFile(projectRoot: string): boolean {\n const kirographDir = path.join(projectRoot, '.kirograph');\n const envPath = path.join(kirographDir, '.env');\n if (fs.existsSync(envPath)) return false;\n\n ensureDir(kirographDir);\n fs.writeFileSync(envPath, [\n '# KiroGraph \u2014 jev (TypeSafe System One) API key',\n \"# Used by memoryRelationMode / wikiContradictionMode / securityAuthDetectionMode: 'jev'\",\n '# Get a key at https://docs.typesafe.ai \u2014 this file should never be committed to git.',\n 'JEV_API_KEY=',\n '',\n ].join('\\n'));\n\n const gitignorePath = path.join(projectRoot, '.gitignore');\n if (fs.existsSync(gitignorePath)) {\n const content = fs.readFileSync(gitignorePath, 'utf8');\n if (!content.includes('.kirograph/.env')) {\n const sep = content.length === 0 || content.endsWith('\\n') ? '' : '\\n';\n fs.appendFileSync(gitignorePath, `${sep}.kirograph/.env\\n`);\n }\n }\n\n return true;\n}\n\nexport function readJson(p: string): any {\n try { return JSON.parse(fs.readFileSync(p, 'utf8')); } catch { return {}; }\n}\n\nexport function writeJson(p: string, data: unknown): void {\n fs.writeFileSync(p, JSON.stringify(data, null, 2) + '\\n');\n}\n\n/**\n * Write MCP server config to a JSON file under the mcpServers key.\n * Returns true if the config was written, false if already configured (idempotent).\n */\nexport function writeMcpServersConfig(configPath: string, serverConfig: object): boolean {\n ensureDir(path.dirname(configPath));\n const existing = readJson(configPath);\n existing.mcpServers = existing.mcpServers ?? {};\n if (existing.mcpServers[KIROGRAPH_SERVER_NAME]) {\n return false; // Already configured\n }\n existing.mcpServers[KIROGRAPH_SERVER_NAME] = serverConfig;\n writeJson(configPath, existing);\n return true;\n}\n\n/**\n * Always write (overwrite) the MCP server config entry, regardless of whether it already exists.\n * Used when the final state is known upfront and idempotency would cause stale data.\n */\nexport function overwriteMcpServersConfig(configPath: string, serverConfig: object): void {\n ensureDir(path.dirname(configPath));\n const existing = readJson(configPath);\n existing.mcpServers = existing.mcpServers ?? {};\n existing.mcpServers[KIROGRAPH_SERVER_NAME] = serverConfig;\n writeJson(configPath, existing);\n}\n\nexport function removeMcpServersConfig(configPath: string): boolean {\n if (!fs.existsSync(configPath)) return false;\n const existing = readJson(configPath);\n if (!existing.mcpServers?.[KIROGRAPH_SERVER_NAME]) return false;\n delete existing.mcpServers[KIROGRAPH_SERVER_NAME];\n writeJson(configPath, existing);\n return true;\n}\n\nexport function appendImportLine(filePath: string, line: string, heading: string): boolean {\n const existing = fs.existsSync(filePath) ? fs.readFileSync(filePath, 'utf8') : '';\n if (existing.includes(line)) return false;\n\n const prefix = existing.length > 0 && !existing.endsWith('\\n') ? '\\n' : '';\n const separator = existing.trim().length > 0 ? '\\n' : '';\n fs.writeFileSync(filePath, existing + prefix + separator + heading + '\\n' + line + '\\n');\n return true;\n}\n\nexport function removeImportLine(filePath: string, line: string): boolean {\n if (!fs.existsSync(filePath)) return false;\n const original = fs.readFileSync(filePath, 'utf8');\n const next = original\n .split('\\n')\n .filter(l => l.trim() !== line)\n .join('\\n')\n .replace(/\\n{3,}/g, '\\n\\n');\n if (next === original) return false;\n fs.writeFileSync(filePath, next.endsWith('\\n') ? next : next + '\\n');\n return true;\n}\n\nexport function upsertGeneratedBlock(filePath: string, blockId: string, heading: string, content: string): boolean {\n const start = `<!-- kirograph:${blockId}:start -->`;\n const end = `<!-- kirograph:${blockId}:end -->`;\n const block = `${start}\\n${heading}\\n\\n${content.trim()}\\n${end}`;\n const existing = fs.existsSync(filePath) ? fs.readFileSync(filePath, 'utf8') : '';\n const pattern = new RegExp(`${escapeRegExp(start)}[\\\\s\\\\S]*?${escapeRegExp(end)}`);\n\n if (pattern.test(existing)) {\n const next = existing.replace(pattern, block);\n if (next === existing) return false;\n fs.writeFileSync(filePath, next.endsWith('\\n') ? next : next + '\\n');\n return true;\n }\n\n const prefix = existing.length > 0 && !existing.endsWith('\\n') ? '\\n' : '';\n const separator = existing.trim().length > 0 ? '\\n' : '';\n fs.writeFileSync(filePath, existing + prefix + separator + block + '\\n');\n return true;\n}\n\nexport function removeGeneratedBlock(filePath: string, blockId: string): boolean {\n if (!fs.existsSync(filePath)) return false;\n const start = `<!-- kirograph:${blockId}:start -->`;\n const end = `<!-- kirograph:${blockId}:end -->`;\n const original = fs.readFileSync(filePath, 'utf8');\n const pattern = new RegExp(`\\\\n?${escapeRegExp(start)}[\\\\s\\\\S]*?${escapeRegExp(end)}\\\\n?`);\n const next = original.replace(pattern, '\\n').replace(/\\n{3,}/g, '\\n\\n');\n if (next === original) return false;\n fs.writeFileSync(filePath, next.endsWith('\\n') ? next : next + '\\n');\n return true;\n}\n\nfunction escapeRegExp(s: string): string {\n return s.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\$&');\n}\n\n/**\n * Build InstructionOptions from the installLate parameters.\n * Used by all targets to pass full feature config to buildAgentInstructions.\n */\nexport function buildInstructionOpts(opts: LateInstallOptions, hasHooks?: boolean): InstructionOptions {\n return {\n cavemanMode: opts.cavemanMode,\n shellCompressionLevel: (opts.shellCompressionLevel as InstructionOptions['shellCompressionLevel']) ?? undefined,\n enableArchitecture: opts.enableArchitecture ?? false,\n enableMemory: opts.enableMemory ?? false,\n enableDocs: opts.enableDocs ?? false,\n enableData: opts.enableData ?? false,\n enableSecurity: opts.enableSecurity ?? false,\n enablePatterns: opts.enablePatterns ?? false,\n enableWiki: opts.enableWiki ?? false,\n enableCodeHealth: opts.enableCodeHealth ?? false,\n enableNavigation: opts.enableNavigation ?? false,\n enableComplexity: opts.enableComplexity ?? false,\n enableGitContext: opts.enableGitContext ?? false,\n enableEditPrimitives: opts.enableEditPrimitives ?? false,\n enableBranch: opts.enableBranch ?? false,\n enableAgentUtils: opts.enableAgentUtils ?? false,\n enableGeneralCompression: opts.enableGeneralCompression ?? false,\n trackCallSites: opts.trackCallSites ?? false,\n hasHooks: hasHooks ?? false,\n };\n}\n\nconst violet = '\\x1b[38;5;99m';\nconst resetAnsi = '\\x1b[0m';\nconst dimAnsi = '\\x1b[2m';\nconst boldAnsi = '\\x1b[1m';\n\n/**\n * Print a highlighted MCP config JSON block for targets that need user-scoped setup.\n */\nexport function printMcpSetup(configPath: string, projectRoot: string): void {\n const escapedPath = projectRoot.replace(/\\\\/g, '\\\\\\\\').replace(/\"/g, '\\\\\"');\n console.log(`\\n ${dimAnsi}Add the MCP server manually:${resetAnsi}`);\n console.log(` ${dimAnsi}Edit${resetAnsi} ${violet}${boldAnsi}${configPath}${resetAnsi} ${dimAnsi}and add:${resetAnsi}`);\n console.log(` ${violet}{${resetAnsi}`);\n console.log(` ${violet} \"mcpServers\": {${resetAnsi}`);\n console.log(` ${violet} \"kirograph\": {${resetAnsi}`);\n console.log(` ${violet} \"command\": \"kirograph\",${resetAnsi}`);\n console.log(` ${violet} \"args\": [\"serve\", \"--mcp\", \"--path\", \"${escapedPath}\"]${resetAnsi}`);\n console.log(` ${violet} }${resetAnsi}`);\n console.log(` ${violet} }${resetAnsi}`);\n console.log(` ${violet}}${resetAnsi}\\n`);\n}\n\n/**\n * Print a highlighted CLI command for MCP registration.\n */\nexport function printMcpCommand(command: string): void {\n console.log(`\\n ${dimAnsi}Add the MCP server with:${resetAnsi}`);\n console.log(` ${violet}${boldAnsi}${command}${resetAnsi}\\n`);\n}\n"],
5
+ "mappings": ";;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAAoB;AACpB,WAAsB;AACtB,wBAAqC;AAiC9B,MAAM,wBAAwB;AAC9B,MAAM,oBAAoB;AAC1B,MAAM,qBAAqB,CAAC,SAAS,OAAO;AAiB5C,SAAS,cAAc,aAA6B;AACzD,QAAM,YAAY,QAAQ,aAAa;AACvC,SAAO,YACH,GAAG,WAAW,4BACd,GAAG,WAAW;AACpB;AAEO,MAAM,qBAAqB,cAAc,iCAAiC;AAC1E,MAAM,kBAAkB;AACxB,MAAM,yBAAyB,uCAAqB,IAAI,UAAQ,cAAc,IAAI,EAAE;AAEpF,SAAS,UAAU,GAAiB;AACzC,KAAG,UAAU,GAAG,EAAE,WAAW,KAAK,CAAC;AACrC;AAaO,SAAS,iBAAiB,aAA8B;AAC7D,QAAM,eAAe,KAAK,KAAK,aAAa,YAAY;AACxD,QAAM,UAAU,KAAK,KAAK,cAAc,MAAM;AAC9C,MAAI,GAAG,WAAW,OAAO,EAAG,QAAO;AAEnC,YAAU,YAAY;AACtB,KAAG,cAAc,SAAS;AAAA,IACxB;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF,EAAE,KAAK,IAAI,CAAC;AAEZ,QAAM,gBAAgB,KAAK,KAAK,aAAa,YAAY;AACzD,MAAI,GAAG,WAAW,aAAa,GAAG;AAChC,UAAM,UAAU,GAAG,aAAa,eAAe,MAAM;AACrD,QAAI,CAAC,QAAQ,SAAS,iBAAiB,GAAG;AACxC,YAAM,MAAM,QAAQ,WAAW,KAAK,QAAQ,SAAS,IAAI,IAAI,KAAK;AAClE,SAAG,eAAe,eAAe,GAAG,GAAG;AAAA,CAAmB;AAAA,IAC5D;AAAA,EACF;AAEA,SAAO;AACT;AAEO,SAAS,SAAS,GAAgB;AACvC,MAAI;AAAE,WAAO,KAAK,MAAM,GAAG,aAAa,GAAG,MAAM,CAAC;AAAA,EAAG,QAAQ;AAAE,WAAO,CAAC;AAAA,EAAG;AAC5E;AAEO,SAAS,UAAU,GAAW,MAAqB;AACxD,KAAG,cAAc,GAAG,KAAK,UAAU,MAAM,MAAM,CAAC,IAAI,IAAI;AAC1D;AAMO,SAAS,sBAAsB,YAAoB,cAA+B;AACvF,YAAU,KAAK,QAAQ,UAAU,CAAC;AAClC,QAAM,WAAW,SAAS,UAAU;AACpC,WAAS,aAAa,SAAS,cAAc,CAAC;AAC9C,MAAI,SAAS,WAAW,qBAAqB,GAAG;AAC9C,WAAO;AAAA,EACT;AACA,WAAS,WAAW,qBAAqB,IAAI;AAC7C,YAAU,YAAY,QAAQ;AAC9B,SAAO;AACT;AAMO,SAAS,0BAA0B,YAAoB,cAA4B;AACxF,YAAU,KAAK,QAAQ,UAAU,CAAC;AAClC,QAAM,WAAW,SAAS,UAAU;AACpC,WAAS,aAAa,SAAS,cAAc,CAAC;AAC9C,WAAS,WAAW,qBAAqB,IAAI;AAC7C,YAAU,YAAY,QAAQ;AAChC;AAEO,SAAS,uBAAuB,YAA6B;AAClE,MAAI,CAAC,GAAG,WAAW,UAAU,EAAG,QAAO;AACvC,QAAM,WAAW,SAAS,UAAU;AACpC,MAAI,CAAC,SAAS,aAAa,qBAAqB,EAAG,QAAO;AAC1D,SAAO,SAAS,WAAW,qBAAqB;AAChD,YAAU,YAAY,QAAQ;AAC9B,SAAO;AACT;AAEO,SAAS,iBAAiB,UAAkB,MAAc,SAA0B;AACzF,QAAM,WAAW,GAAG,WAAW,QAAQ,IAAI,GAAG,aAAa,UAAU,MAAM,IAAI;AAC/E,MAAI,SAAS,SAAS,IAAI,EAAG,QAAO;AAEpC,QAAM,SAAS,SAAS,SAAS,KAAK,CAAC,SAAS,SAAS,IAAI,IAAI,OAAO;AACxE,QAAM,YAAY,SAAS,KAAK,EAAE,SAAS,IAAI,OAAO;AACtD,KAAG,cAAc,UAAU,WAAW,SAAS,YAAY,UAAU,OAAO,OAAO,IAAI;AACvF,SAAO;AACT;AAEO,SAAS,iBAAiB,UAAkB,MAAuB;AACxE,MAAI,CAAC,GAAG,WAAW,QAAQ,EAAG,QAAO;AACrC,QAAM,WAAW,GAAG,aAAa,UAAU,MAAM;AACjD,QAAM,OAAO,SACV,MAAM,IAAI,EACV,OAAO,OAAK,EAAE,KAAK,MAAM,IAAI,EAC7B,KAAK,IAAI,EACT,QAAQ,WAAW,MAAM;AAC5B,MAAI,SAAS,SAAU,QAAO;AAC9B,KAAG,cAAc,UAAU,KAAK,SAAS,IAAI,IAAI,OAAO,OAAO,IAAI;AACnE,SAAO;AACT;AAEO,SAAS,qBAAqB,UAAkB,SAAiB,SAAiB,SAA0B;AACjH,QAAM,QAAQ,kBAAkB,OAAO;AACvC,QAAM,MAAM,kBAAkB,OAAO;AACrC,QAAM,QAAQ,GAAG,KAAK;AAAA,EAAK,OAAO;AAAA;AAAA,EAAO,QAAQ,KAAK,CAAC;AAAA,EAAK,GAAG;AAC/D,QAAM,WAAW,GAAG,WAAW,QAAQ,IAAI,GAAG,aAAa,UAAU,MAAM,IAAI;AAC/E,QAAM,UAAU,IAAI,OAAO,GAAG,aAAa,KAAK,CAAC,aAAa,aAAa,GAAG,CAAC,EAAE;AAEjF,MAAI,QAAQ,KAAK,QAAQ,GAAG;AAC1B,UAAM,OAAO,SAAS,QAAQ,SAAS,KAAK;AAC5C,QAAI,SAAS,SAAU,QAAO;AAC9B,OAAG,cAAc,UAAU,KAAK,SAAS,IAAI,IAAI,OAAO,OAAO,IAAI;AACnE,WAAO;AAAA,EACT;AAEA,QAAM,SAAS,SAAS,SAAS,KAAK,CAAC,SAAS,SAAS,IAAI,IAAI,OAAO;AACxE,QAAM,YAAY,SAAS,KAAK,EAAE,SAAS,IAAI,OAAO;AACtD,KAAG,cAAc,UAAU,WAAW,SAAS,YAAY,QAAQ,IAAI;AACvE,SAAO;AACT;AAEO,SAAS,qBAAqB,UAAkB,SAA0B;AAC/E,MAAI,CAAC,GAAG,WAAW,QAAQ,EAAG,QAAO;AACrC,QAAM,QAAQ,kBAAkB,OAAO;AACvC,QAAM,MAAM,kBAAkB,OAAO;AACrC,QAAM,WAAW,GAAG,aAAa,UAAU,MAAM;AACjD,QAAM,UAAU,IAAI,OAAO,OAAO,aAAa,KAAK,CAAC,aAAa,aAAa,GAAG,CAAC,MAAM;AACzF,QAAM,OAAO,SAAS,QAAQ,SAAS,IAAI,EAAE,QAAQ,WAAW,MAAM;AACtE,MAAI,SAAS,SAAU,QAAO;AAC9B,KAAG,cAAc,UAAU,KAAK,SAAS,IAAI,IAAI,OAAO,OAAO,IAAI;AACnE,SAAO;AACT;AAEA,SAAS,aAAa,GAAmB;AACvC,SAAO,EAAE,QAAQ,uBAAuB,MAAM;AAChD;AAMO,SAAS,qBAAqB,MAA0B,UAAwC;AACrG,SAAO;AAAA,IACL,aAAa,KAAK;AAAA,IAClB,uBAAwB,KAAK,yBAAyE;AAAA,IACtG,oBAAoB,KAAK,sBAAsB;AAAA,IAC/C,cAAc,KAAK,gBAAgB;AAAA,IACnC,YAAY,KAAK,cAAc;AAAA,IAC/B,YAAY,KAAK,cAAc;AAAA,IAC/B,gBAAgB,KAAK,kBAAkB;AAAA,IACvC,gBAAgB,KAAK,kBAAkB;AAAA,IACvC,YAAY,KAAK,cAAc;AAAA,IAC/B,kBAAkB,KAAK,oBAAoB;AAAA,IAC3C,kBAAkB,KAAK,oBAAoB;AAAA,IAC3C,kBAAkB,KAAK,oBAAoB;AAAA,IAC3C,kBAAkB,KAAK,oBAAoB;AAAA,IAC3C,sBAAsB,KAAK,wBAAwB;AAAA,IACnD,cAAc,KAAK,gBAAgB;AAAA,IACnC,kBAAkB,KAAK,oBAAoB;AAAA,IAC3C,0BAA0B,KAAK,4BAA4B;AAAA,IAC3D,gBAAgB,KAAK,kBAAkB;AAAA,IACvC,UAAU,YAAY;AAAA,EACxB;AACF;AAEA,MAAM,SAAS;AACf,MAAM,YAAY;AAClB,MAAM,UAAU;AAChB,MAAM,WAAW;AAKV,SAAS,cAAc,YAAoB,aAA2B;AAC3E,QAAM,cAAc,YAAY,QAAQ,OAAO,MAAM,EAAE,QAAQ,MAAM,KAAK;AAC1E,UAAQ,IAAI;AAAA,IAAO,OAAO,+BAA+B,SAAS,EAAE;AACpE,UAAQ,IAAI,KAAK,OAAO,OAAO,SAAS,IAAI,MAAM,GAAG,QAAQ,GAAG,UAAU,GAAG,SAAS,IAAI,OAAO,WAAW,SAAS,EAAE;AACvH,UAAQ,IAAI,KAAK,MAAM,IAAI,SAAS,EAAE;AACtC,UAAQ,IAAI,KAAK,MAAM,oBAAoB,SAAS,EAAE;AACtD,UAAQ,IAAI,KAAK,MAAM,qBAAqB,SAAS,EAAE;AACvD,UAAQ,IAAI,KAAK,MAAM,gCAAgC,SAAS,EAAE;AAClE,UAAQ,IAAI,KAAK,MAAM,+CAA+C,WAAW,KAAK,SAAS,EAAE;AACjG,UAAQ,IAAI,KAAK,MAAM,QAAQ,SAAS,EAAE;AAC1C,UAAQ,IAAI,KAAK,MAAM,MAAM,SAAS,EAAE;AACxC,UAAQ,IAAI,KAAK,MAAM,IAAI,SAAS;AAAA,CAAI;AAC1C;AAKO,SAAS,gBAAgB,SAAuB;AACrD,UAAQ,IAAI;AAAA,IAAO,OAAO,2BAA2B,SAAS,EAAE;AAChE,UAAQ,IAAI,KAAK,MAAM,GAAG,QAAQ,GAAG,OAAO,GAAG,SAAS;AAAA,CAAI;AAC9D;",
6
6
  "names": []
7
7
  }
@@ -193,6 +193,24 @@ async function promptEmbeddings(rl) {
193
193
  }
194
194
  return patch;
195
195
  }
196
+ async function promptJevClassification(rl, patch) {
197
+ const targets = [];
198
+ if (patch.enableMemory) targets.push("memory relation judging");
199
+ if (patch.enableWiki) targets.push("wiki contradiction detection");
200
+ if (patch.enableSecurity) targets.push("attack-surface auth detection");
201
+ if (targets.length === 0) return;
202
+ (0, import_prompts.printSection)("\u{1F9EA}", "jev Classification (experimental)");
203
+ const enableJev = await (0, import_prompts.askToggle)(
204
+ rl,
205
+ `jev-powered classification for: ${targets.join(", ")}?`,
206
+ "\u26A0 Experimental. jev (TypeSafe System One, https://docs.typesafe.ai) is a fast typed-classification model that replaces a heuristic or agent-reasoning step with a real judgment call for each of the modules above. Requires a paid third-party API key \u2014 a .kirograph/.env file will be created for you to add JEV_API_KEY after install. Falls back to each module's existing non-jev behavior whenever the key is unset.",
207
+ false
208
+ );
209
+ if (!enableJev) return;
210
+ if (patch.enableMemory) patch.memoryRelationMode = "jev";
211
+ if (patch.enableWiki) patch.wikiContradictionMode = "jev";
212
+ if (patch.enableSecurity) patch.securityAuthDetectionMode = "jev";
213
+ }
196
214
  async function promptConfigOptions(rl, opts = {}) {
197
215
  const installMode = await (0, import_prompts.arrowSelect)(rl, "Installation mode:", [
198
216
  { value: "core", label: "Core only", description: "3 always-on tools (search, context, node) \u2014 ~170 tok. Zero config." },
@@ -236,7 +254,10 @@ async function promptConfigOptions(rl, opts = {}) {
236
254
  enableEditPrimitives: false,
237
255
  enableBranch: false,
238
256
  enableAgentUtils: false,
239
- enableGeneralCompression: false
257
+ enableGeneralCompression: false,
258
+ memoryRelationMode: "agent",
259
+ wikiContradictionMode: "heuristic",
260
+ securityAuthDetectionMode: "heuristic"
240
261
  };
241
262
  if (installMode === "core") {
242
263
  const embeddingPatch2 = await promptEmbeddings(rl);
@@ -268,6 +289,7 @@ async function promptConfigOptions(rl, opts = {}) {
268
289
  enableWiki: true,
269
290
  wikiSynthesisMode: "agent"
270
291
  };
292
+ await promptJevClassification(rl, fullPatch);
271
293
  return { patch: fullPatch, hooksToImport: null };
272
294
  }
273
295
  if (installMode === "profiles") {
@@ -279,6 +301,7 @@ async function promptConfigOptions(rl, opts = {}) {
279
301
  const profile = PROFILES[profileKey];
280
302
  const embeddingPatch2 = await promptEmbeddings(rl);
281
303
  const patch2 = { ...basePatch, ...profile.patch, ...embeddingPatch2 };
304
+ await promptJevClassification(rl, patch2);
282
305
  return { patch: patch2, hooksToImport: null };
283
306
  }
284
307
  const embeddingPatch = await promptEmbeddings(rl);
@@ -573,6 +596,7 @@ async function promptConfigOptions(rl, opts = {}) {
573
596
  }
574
597
  }
575
598
  }
599
+ await promptJevClassification(rl, patch);
576
600
  return { patch, hooksToImport };
577
601
  }
578
602
  // Annotate the CommonJS export names for ESM import in node:
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/bin/installer/config-prompt.ts"],
4
- "sourcesContent": ["/**\n * KiroGraph Installer \u2014 configuration prompting\n */\n\nimport * as readline from 'readline';\nimport { KiroGraphConfig } from '../../config';\ntype CavemanMode = 'lite' | 'full' | 'ultra';\nimport { ask, askToggle, arrowSelect, printSection, printSeparator, dim, reset, violet } from './prompts';\nimport { promptImportGlobalHookSelection } from '../../hooks/import-prompt';\n\nexport interface PromptConfigOptions {\n projectRoot?: string;\n offerHookImport?: boolean;\n}\nexport type ConfigPatch = Pick<KiroGraphConfig,\n 'enableEmbeddings' | 'useVecIndex' | 'semanticEngine' |\n 'turboquantMemDocs' | 'turboquantBits' | 'turbovecMemDocs' | 'turbovecBits' |\n 'typesenseDashboard' | 'qdrantDashboard' |\n 'extractDocstrings' | 'trackCallSites' | 'enableArchitecture' |\n 'cavemanMode' | 'shellCompressionLevel' |\n 'enableMemory' | 'enableWatchmen' | 'watchmenThreshold' | 'watchmenSynthesisMode' | 'watchmenLocalModel' |\n 'enableDocs' | 'docsContextLimit' |\n 'enableData' | 'dataContextLimit' |\n 'enableSecurity' | 'enablePatterns' |\n 'enableWiki' | 'wikiSynthesisMode' | 'wikiLocalModel' |\n 'enableCodeHealth' | 'enableNavigation' | 'enableComplexity' |\n 'enableGitContext' | 'enableEditPrimitives' | 'enableBranch' |\n 'enableAgentUtils' | 'enableGeneralCompression'\n> & { embeddingModel?: string; embeddingDim?: number };\nexport type SemanticEngine = KiroGraphConfig['semanticEngine'];\n\ntype InstallMode = 'core' | 'full' | 'custom' | 'profiles';\n\nconst PROFILES: Record<string, { label: string; description: string; patch: Partial<ConfigPatch> }> = {\n developer: {\n label: 'Developer',\n description: 'Code health, navigation, complexity, call-site tracking',\n patch: { enableCodeHealth: true, enableNavigation: true, enableComplexity: true, trackCallSites: true },\n },\n team: {\n label: 'Team',\n description: 'Developer + architecture, git context, wiki',\n patch: { enableCodeHealth: true, enableNavigation: true, enableComplexity: true, trackCallSites: true, enableArchitecture: true, enableGitContext: true, enableWiki: true, wikiSynthesisMode: 'agent' },\n },\n security: {\n label: 'Security',\n description: 'Security analysis, patterns, architecture, code health',\n patch: { enableSecurity: true, enableArchitecture: true, enablePatterns: true, enableCodeHealth: true },\n },\n data: {\n label: 'Data & Docs',\n description: 'Tabular data indexing and documentation navigation',\n patch: { enableData: true, enableDocs: true },\n },\n ai: {\n label: 'AI / LLM Agent',\n description: 'Memory, watchmen, agent utils, wiki, general compression',\n patch: { enableMemory: true, enableWatchmen: true, enableAgentUtils: true, enableWiki: true, wikiSynthesisMode: 'agent', enableGeneralCompression: true },\n },\n};\n\nexport const DEFAULT_EMBEDDING_MODEL = 'nomic-ai/nomic-embed-text-v1.5';\n\n/** Well-known embedding models with their output dimensions. */\nconst PRESET_MODELS = [\n {\n value: 'nomic-ai/nomic-embed-text-v1.5',\n label: 'nomic-embed-text-v1.5',\n dim: 768,\n description: '768-dim \u00B7 ~130MB \u00B7 Best quality for code search (recommended)',\n },\n {\n value: 'onnx-community/embeddinggemma-300m-ONNX',\n label: 'embeddinggemma-300m',\n dim: 768,\n description: '768-dim \u00B7 ~300MB \u00B7 Google Gemma-based, multilingual, 2048-token context',\n },\n {\n value: 'Xenova/all-MiniLM-L6-v2',\n label: 'all-MiniLM-L6-v2',\n dim: 384,\n description: '384-dim \u00B7 ~23MB \u00B7 Fast and lightweight, lower accuracy',\n },\n {\n value: 'BAAI/bge-base-en-v1.5',\n label: 'bge-base-en-v1.5',\n dim: 768,\n description: '768-dim \u00B7 ~110MB \u00B7 Strong general-purpose alternative to nomic',\n },\n {\n value: '__other__',\n label: 'Other',\n dim: 768,\n description: 'Enter a custom HuggingFace model ID and embedding dimension',\n },\n] as const;\n\ntype EmbeddingPatch = Pick<ConfigPatch,\n 'enableEmbeddings' | 'embeddingModel' | 'embeddingDim' | 'semanticEngine' | 'useVecIndex' |\n 'turboquantMemDocs' | 'turboquantBits' | 'turbovecMemDocs' | 'turbovecBits' |\n 'typesenseDashboard' | 'qdrantDashboard'\n>;\n\n/**\n * Semantic embeddings are a core feature, not a \"custom\"-only extra \u2014 asked\n * for every install mode (core, full, profiles, custom) so users always get\n * to pick whether embeddings run and, if so, which model/engine.\n */\nasync function promptEmbeddings(rl: readline.Interface): Promise<EmbeddingPatch> {\n printSection('\uD83D\uDD0D', 'Semantic Search');\n\n const enableEmbeddings = await askToggle(\n rl,\n 'Semantic embeddings (similarity search):',\n 'Enables natural-language code search via vector embeddings. A local model (~130MB) is downloaded on first use.',\n );\n\n const patch: EmbeddingPatch = {\n enableEmbeddings,\n semanticEngine: 'cosine',\n useVecIndex: false,\n turboquantMemDocs: false, turboquantBits: 3,\n turbovecMemDocs: false, turbovecBits: 4,\n typesenseDashboard: false, qdrantDashboard: false,\n };\n\n if (!enableEmbeddings) {\n return patch;\n }\n\n // \u2500\u2500 Model selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const modelChoice = await arrowSelect<string>(\n rl,\n 'Embedding model:',\n PRESET_MODELS.map(m => ({ value: m.value, label: m.label, description: m.description })),\n );\n\n let embeddingModel: string;\n let embeddingDim: number;\n\n if (modelChoice === '__other__') {\n console.log(`\\n ${dim}Enter a HuggingFace model ID in the format org/model-name.${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Model identifier:${reset} `)).trim();\n if (raw.includes('/')) { embeddingModel = raw; break; }\n console.log(` Expected a HuggingFace model ID in the format org/model-name (e.g. nomic-ai/nomic-embed-text-v1.5).`);\n }\n console.log(`\\n ${dim}Enter the embedding output dimension for this model (check the model card on HuggingFace).${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Embedding dimension (e.g. 768, 384):${reset} `)).trim();\n const n = parseInt(raw, 10);\n if (!isNaN(n) && n > 0) { embeddingDim = n; break; }\n console.log(` Expected a positive integer (e.g. 768, 384, 1536).`);\n }\n } else {\n const preset = PRESET_MODELS.find(m => m.value === modelChoice)!;\n embeddingModel = preset.value;\n embeddingDim = preset.dim;\n }\n\n patch.embeddingModel = embeddingModel;\n patch.embeddingDim = embeddingDim;\n\n // \u2500\u2500 Engine selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const semanticEngine = await arrowSelect<SemanticEngine>(rl, 'Vector search engine:', [\n { value: 'cosine', label: 'cosine', description: 'In-process cosine similarity. No extra deps. Best for small/medium projects.' },\n { value: 'turboquant', label: 'turboquant', description: 'ANN index, zero native deps. Compresses embeddings 20\u201330\u00D7 (Google TurboQuant). ANN without native binaries \u2014 ideal for CI, ARM, restricted envs. Optional: npm install turboquant-js.' },\n { value: 'turbovec', label: 'turbovec', description: 'ANN search via Rust/SIMD (napi-rs). Same TurboQuant algorithm but NEON on ARM and AVX-512BW on x86 \u2014 faster than turboquant-js at the cost of a one-time Rust build. Requires Rust toolchain. Build: cd native/turbovec-node && npm install && npm run build.' },\n { value: 'sqlite-vec', label: 'sqlite-vec', description: 'ANN index. Sub-linear search. Best for large codebases. Needs: better-sqlite3, sqlite-vec (native).' },\n { value: 'orama', label: 'orama', description: 'Hybrid search (full-text + vector). Pure JS. Needs: @orama/orama, @orama/plugin-data-persistence.' },\n { value: 'pglite', label: 'pglite', description: 'Hybrid search via PostgreSQL + pgvector. Exact results. Pure WASM. Needs: @electric-sql/pglite.' },\n { value: 'lancedb', label: 'lancedb', description: 'ANN search via LanceDB (Apache Lance columnar format). Pure JS. Needs: @lancedb/lancedb.' },\n { value: 'qdrant', label: 'qdrant', description: 'ANN search via Qdrant embedded binary (HNSW index, Cosine). Needs: qdrant-local.' },\n { value: 'typesense', label: 'typesense', description: 'ANN search via Typesense (auto-downloaded binary, HNSW, Cosine). Needs: typesense.' },\n ]);\n patch.semanticEngine = semanticEngine;\n patch.useVecIndex = semanticEngine === 'sqlite-vec';\n\n // TurboQuant for memory & docs: offer only when turboquant is the code-node engine\n if (semanticEngine === 'turboquant') {\n patch.turboquantMemDocs = await askToggle(rl,\n 'TurboQuant for memory & docs search (optional):',\n 'Replaces the default linear cosine scan in memory observations and doc sections with a compressed ANN index \u2014 no native deps required. Most useful when you accumulate many observations or large doc sets (1 000+ entries).',\n false,\n );\n }\n\n // TurboVec bit width\n if (semanticEngine === 'turbovec') {\n patch.turbovecBits = await arrowSelect<number>(rl, 'TurboVec bits per coordinate:', [\n { value: 4, label: '4 bits (recommended)', description: 'Best quality, ~19\u00D7 compression vs raw Float32. Default.' },\n { value: 3, label: '3 bits', description: 'Balanced \u2014 ~25\u00D7 compression, slight quality drop.' },\n { value: 2, label: '2 bits', description: 'Highest compression (~38\u00D7), lowest accuracy.' },\n ]);\n patch.turbovecMemDocs = await askToggle(rl,\n 'TurboVec for memory & docs search (optional):',\n 'Replaces the default linear cosine scan in memory observations and doc sections with the TurboVec ANN index. Requires the addon to be built.',\n false,\n );\n }\n\n if (semanticEngine === 'typesense') {\n patch.typesenseDashboard = await askToggle(rl,\n 'Typesense dashboard:',\n 'Serves the Typesense Dashboard locally and opens it in your browser after indexing completes.',\n false,\n );\n }\n\n if (semanticEngine === 'qdrant') {\n patch.qdrantDashboard = await askToggle(rl,\n 'Qdrant dashboard:',\n 'Downloads the Qdrant Web UI (first time only) and opens it in your browser after indexing completes.',\n false,\n );\n }\n\n return patch;\n}\n\nexport async function promptConfigOptions(\n rl: readline.Interface,\n opts: PromptConfigOptions = {},\n): Promise<{ patch: ConfigPatch; hooksToImport: string[] | null }> {\n // \u2500\u2500 Install mode \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const installMode = await arrowSelect<InstallMode>(rl, 'Installation mode:', [\n { value: 'core', label: 'Core only', description: '3 always-on tools (search, context, node) \u2014 ~170 tok. Zero config.' },\n { value: 'full', label: 'Full', description: 'Enable every feature with sensible defaults. Best for a fresh project.' },\n { value: 'profiles', label: 'Profiles', description: 'Choose a preset bundle (Developer, Team, Security, Data & Docs, AI/LLM).' },\n { value: 'custom', label: 'Custom', description: 'Answer each question individually. Maximum control.' },\n ]);\n\n const basePatch: ConfigPatch = {\n enableEmbeddings: false, useVecIndex: false, semanticEngine: 'cosine',\n turboquantMemDocs: false, turboquantBits: 3, turbovecMemDocs: false, turbovecBits: 4,\n typesenseDashboard: false, qdrantDashboard: false,\n extractDocstrings: false, trackCallSites: false,\n enableArchitecture: false, cavemanMode: 'off', shellCompressionLevel: 'off',\n enableMemory: false, enableWatchmen: false, watchmenThreshold: 5,\n watchmenSynthesisMode: 'local', watchmenLocalModel: 'onnx-community/gemma-4-E4B-it-ONNX',\n enableDocs: false, docsContextLimit: 0,\n enableData: false, dataContextLimit: 0,\n enableSecurity: false, enablePatterns: false,\n enableWiki: false, wikiSynthesisMode: 'agent', wikiLocalModel: 'onnx-community/gemma-4-E4B-it-ONNX',\n enableCodeHealth: false, enableNavigation: false, enableComplexity: false,\n enableGitContext: false, enableEditPrimitives: false, enableBranch: false,\n enableAgentUtils: false, enableGeneralCompression: false,\n };\n\n if (installMode === 'core') {\n const embeddingPatch = await promptEmbeddings(rl);\n return { patch: { ...basePatch, ...embeddingPatch }, hooksToImport: null };\n }\n\n if (installMode === 'full') {\n const embeddingPatch = await promptEmbeddings(rl);\n const fullPatch: ConfigPatch = {\n ...basePatch,\n ...embeddingPatch,\n extractDocstrings: true, trackCallSites: true,\n enableArchitecture: true, shellCompressionLevel: 'normal',\n enableCodeHealth: true, enableNavigation: true, enableComplexity: true,\n enableGitContext: true, enableEditPrimitives: true, enableBranch: true,\n enableAgentUtils: true, enableGeneralCompression: true,\n enableSecurity: true, enablePatterns: true,\n enableDocs: true, enableData: true,\n enableMemory: true, enableWatchmen: true,\n enableWiki: true, wikiSynthesisMode: 'agent',\n };\n return { patch: fullPatch, hooksToImport: null };\n }\n\n if (installMode === 'profiles') {\n const profileKey = await arrowSelect<string>(rl, 'Select a profile:', Object.entries(PROFILES).map(([key, p]) => ({\n value: key,\n label: p.label,\n description: p.description,\n })));\n const profile = PROFILES[profileKey];\n const embeddingPatch = await promptEmbeddings(rl);\n const patch: ConfigPatch = { ...basePatch, ...profile.patch, ...embeddingPatch };\n return { patch, hooksToImport: null };\n }\n\n // \u2500\u2500 Custom: ask all questions individually \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const embeddingPatch = await promptEmbeddings(rl);\n const patch: ConfigPatch = { ...basePatch, ...embeddingPatch };\n\n // \u2500\u2500 Graph Features \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCCA', 'Graph Features');\n\n patch.extractDocstrings = await askToggle(rl,\n 'Docstring extraction:',\n 'Enriches symbol metadata and improves context quality. Slightly increases indexing time.',\n false,\n );\n\n patch.trackCallSites = await askToggle(rl,\n 'Call site tracking (caller/callee graph):',\n 'Enables kirograph_callers and kirograph_callees MCP tools. Increases index size.',\n false,\n );\n\n patch.enableArchitecture = await askToggle(rl,\n 'Architecture analysis (packages + layers):',\n 'Detects packages from manifests and architectural layers. Enables kirograph_architecture, kirograph_coupling, kirograph_package.',\n false,\n );\n\n // \u2500\u2500 Graph Tools \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCCA', 'Graph Tools');\n\n patch.enableNavigation = await askToggle(rl,\n 'Navigation tools (status, files, impact):',\n 'Enables kirograph_status, kirograph_files, kirograph_impact.',\n false,\n );\n\n patch.enableCodeHealth = await askToggle(rl,\n 'Code health tools (hotspots, dead code, path analysis, type hierarchy):',\n 'Enables kirograph_hotspots, kirograph_surprising, kirograph_diff, kirograph_dead_code, kirograph_circular_deps, kirograph_path, kirograph_affected, kirograph_type_hierarchy.',\n false,\n );\n\n patch.enableComplexity = await askToggle(rl,\n 'Complexity metrics tools:',\n 'Enables complexity analysis, simplify scan, health score, DSM, test risk.',\n false,\n );\n\n patch.enableGitContext = await askToggle(rl,\n 'Git context tools (diff context, commit context, flows):',\n 'Enables kirograph_flows, kirograph_diff_context, kirograph_commit_context, kirograph_pr_context, kirograph_changelog, kirograph_test_map, kirograph_test_coverage.',\n false,\n );\n\n patch.enableEditPrimitives = await askToggle(rl,\n 'Edit primitive tools (str_replace, insert_at, refactor):',\n 'Enables kirograph_refactor, kirograph_str_replace, kirograph_multi_str_replace, kirograph_insert_at, kirograph_ast_grep_rewrite.',\n false,\n );\n\n patch.enableAgentUtils = await askToggle(rl,\n 'Agent utilities (file caching, budget tracking):',\n 'Enables kirograph_read, kirograph_gain, kirograph_budget.',\n false,\n );\n\n // \u2500\u2500 Security \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDD12', 'Security');\n\n patch.enableSecurity = await askToggle(rl,\n 'Security analysis (vulnerability scanning + reachability):',\n 'Scans dependency manifests for known vulnerabilities and performs reachability analysis. Requires Architecture analysis (will be auto-enabled). Enables kirograph_security, kirograph_vulns, kirograph_sbom, kirograph_vex, kirograph_reachability MCP tools.',\n false,\n );\n\n if (patch.enableSecurity && !patch.enableArchitecture) {\n patch.enableArchitecture = true;\n console.log(' \u2139 Architecture analysis auto-enabled (required by Security module)');\n }\n\n // \u2500\u2500 Pattern Matching \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDD0D', 'Pattern Matching');\n\n patch.enablePatterns = await askToggle(rl,\n 'Precise SAST with ast-grep?',\n 'Runs AST structural pattern matching during indexing using @ast-grep/napi (~15MB native binding). Unlike heuristic symbol-name analysis, matches real code structure \u2014 precise SQL injection, path traversal, eval detection. Requires @ast-grep/napi (will be installed automatically if you answer yes).',\n false,\n );\n\n // \u2500\u2500 Documentation \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCD6', 'Documentation');\n\n (patch as any).enableDocs = await askToggle(rl,\n 'Documentation indexing (section-level retrieval):',\n 'Indexes docs by heading structure. Enables kirograph_docs_toc, kirograph_docs_search, kirograph_docs_section, kirograph_docs_outline, kirograph_docs_refs.',\n false,\n );\n\n if ((patch as any).enableDocs) {\n const contextChoice = await arrowSelect<number>(rl, 'Include doc sections in kirograph_context results?', [\n { value: 0, label: '0 (disabled)', description: 'Docs stay separate \u2014 use kirograph_docs_* tools explicitly (recommended)' },\n { value: 3, label: '3 sections', description: 'Include up to 3 relevant doc sections in context results' },\n { value: 5, label: '5 sections', description: 'Include up to 5 relevant doc sections in context results' },\n { value: 10, label: '10 sections', description: 'Include up to 10 relevant doc sections in context results' },\n ]);\n (patch as any).docsContextLimit = contextChoice;\n }\n\n // \u2500\u2500 Data \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCCA', 'Data');\n\n (patch as any).enableData = await askToggle(rl,\n 'Tabular data indexing (CSV/TSV/JSONL/JSON/Excel/Parquet):',\n 'Indexes data files for structured querying. Enables kirograph_data_list, kirograph_data_describe, kirograph_data_query, kirograph_data_aggregate, kirograph_data_search.',\n false,\n );\n\n if ((patch as any).enableData) {\n (patch as any).dataInstallExcel = await askToggle(rl,\n 'Install Excel support (xlsx package)?',\n 'Required for .xlsx/.xls files. CSV/TSV/JSONL/JSON are always supported without extra deps.',\n false,\n );\n\n (patch as any).dataInstallParquet = await askToggle(rl,\n 'Install Parquet support (parquetjs-lite package)?',\n 'Required for .parquet files. CSV/TSV/JSONL/JSON are always supported without extra deps.',\n false,\n );\n\n (patch as any).dataInstallPdf = await askToggle(rl,\n 'Install PDF support (@firecrawl/pdf-inspector package)?',\n 'Required for .pdf files. Rust/NAPI binary \u2014 prebuilts for linux-x64 and macOS ARM64.',\n false,\n );\n\n const contextChoice = await arrowSelect<number>(rl, 'Include dataset schemas in kirograph_context results?', [\n { value: 0, label: '0 (disabled)', description: 'Data stays separate \u2014 use kirograph_data_* tools explicitly (recommended)' },\n { value: 2, label: '2 datasets', description: 'Include up to 2 relevant dataset schemas in context results' },\n { value: 5, label: '5 datasets', description: 'Include up to 5 relevant dataset schemas in context results' },\n ]);\n (patch as any).dataContextLimit = contextChoice;\n }\n\n // \u2500\u2500 Agent Behavior \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83E\uDD16', 'Agent Behavior');\n\n const cavemanChoice = await arrowSelect(rl, 'Communication style (caveman mode):', [\n { value: 'off', label: 'off', description: 'Normal responses \u2014 no compression' },\n { value: 'lite', label: 'lite', description: 'Compact, no filler, full sentences' },\n { value: 'full', label: 'full', description: 'Fragments, no articles, short synonyms' },\n { value: 'ultra', label: 'ultra', description: 'Max compression, abbreviations, \u2192 for causality' },\n ]);\n patch.cavemanMode = cavemanChoice as CavemanMode | 'off';\n\n const compressionChoice = await arrowSelect(rl, 'Shell compression (kirograph_exec):', [\n { value: 'off', label: 'off', description: 'Disables kirograph_exec entirely' },\n { value: 'normal', label: 'normal', description: 'Balanced: removes noise, keeps structure (recommended)' },\n { value: 'aggressive', label: 'aggressive', description: 'More compact: groups by category, limits output' },\n { value: 'ultra', label: 'ultra', description: 'Maximum compression: counts and summaries only' },\n ]);\n patch.shellCompressionLevel = compressionChoice as KiroGraphConfig['shellCompressionLevel'];\n if (compressionChoice === 'off') {\n console.log(' \u2139 kirograph_exec disabled (shell compression is off)');\n }\n\n patch.enableGeneralCompression = await askToggle(rl,\n 'General-purpose compression tool (kirograph_compress):',\n 'Enables kirograph_compress \u2014 an on-demand MCP tool that compresses arbitrary text before it reaches the model. ' +\n 'Two engines: rtk-style structural filters for shell output (git, npm, test logs) when a command hint is provided, ' +\n 'or caveman grammar rules for prose and observations otherwise. ' +\n 'Useful when the agent pastes large content, receives a fat RAG chunk, or wants to explicitly compress before storing. ' +\n 'Independent from automatic shell compression (kirograph_exec) and caveman mode \u2014 those apply in the background; ' +\n 'this gives the model an explicit, on-demand compression action.',\n false,\n );\n\n let hooksToImport: string[] | null = null;\n if (opts.offerHookImport && opts.projectRoot) {\n printSection('\uD83E\uDE9D', 'Hooks');\n hooksToImport = await promptImportGlobalHookSelection();\n }\n\n // \u2500\u2500 Memory \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83E\uDDE0', 'Memory');\n\n patch.enableMemory = await askToggle(rl,\n 'Persistent memory (cross-session observations):',\n 'Stores decisions, errors, and patterns across sessions. Compressed (if caveman is on), linked to code symbols, searchable via kirograph_mem_* tools. Zero LLM tokens on write.',\n false,\n );\n\n if (patch.enableMemory) {\n patch.enableWatchmen = await askToggle(rl,\n 'Watchmen (auto-synthesize workspace briefs from memory):',\n 'When enough observations accumulate (default: 5), synthesizes them into .kiro/steering/kirograph-watchmen.md, CLAUDE.md, AGENTS.md, or the equivalent for your tool.',\n false,\n );\n\n if (patch.enableWatchmen) {\n // \u2500\u2500 Synthesis mode \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const synthesisMode = await arrowSelect<KiroGraphConfig['watchmenSynthesisMode']>(\n rl,\n 'Watchmen synthesis mode:',\n [\n {\n value: 'local',\n label: 'Local model',\n description: 'Runs a local HuggingFace model via @huggingface/transformers. Zero API cost, no data leaves your machine. Model downloaded once to ~/.kirograph/models/. Works for all tools via runCommand hook.',\n },\n {\n value: 'agent',\n label: 'Active agent',\n description: '\u26A0 Kiro only. Uses the active Kiro agent to synthesize. Consumes API tokens/credits on every synthesis. Not supported for other tools.',\n },\n ],\n );\n patch.watchmenSynthesisMode = synthesisMode;\n\n if (synthesisMode === 'local') {\n // \u2500\u2500 Local model selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const LOCAL_MODELS = [\n {\n value: 'onnx-community/gemma-4-E4B-it-ONNX',\n label: 'Gemma 4 E4B (recommended)',\n description: '~3\u20134 GB \u00B7 Google DeepMind Gemma 4 \u00B7 4.5B params \u00B7 128K context \u00B7 Best quality \u00B7 Apache 2.0',\n },\n {\n value: 'onnx-community/Qwen2.5-1.5B-Instruct',\n label: 'Qwen2.5-1.5B',\n description: '~1.5 GB \u00B7 Lighter option if RAM is limited \u00B7 Acceptable quality',\n },\n {\n value: 'HuggingFaceTB/SmolLM2-1.7B-Instruct',\n label: 'SmolLM2-1.7B',\n description: '~1.7 GB \u00B7 HuggingFace compact model \u00B7 Good at following structured formats',\n },\n {\n value: '__other__',\n label: 'Other',\n description: 'Enter a custom HuggingFace model ID (must have ONNX weights on onnx-community)',\n },\n ] as const;\n\n const modelChoice = await arrowSelect<string>(rl, 'Local synthesis model:', LOCAL_MODELS.map(m => ({ value: m.value, label: m.label, description: m.description })));\n\n if (modelChoice === '__other__') {\n console.log(`\\n ${dim}Enter a HuggingFace model ID (e.g. onnx-community/gemma-4-E4B-it-ONNX).${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Model identifier:${reset} `)).trim();\n if (raw.includes('/')) { patch.watchmenLocalModel = raw; break; }\n console.log(` Expected a HuggingFace model ID in the format org/model-name.`);\n }\n } else {\n patch.watchmenLocalModel = modelChoice;\n }\n }\n }\n }\n\n // \u2500\u2500 Wiki \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCD6', 'Wiki');\n\n patch.enableWiki = await askToggle(rl,\n 'LLM Wiki (Karpathy-style structured knowledge base):',\n 'Maintains a set of markdown pages that compound knowledge across sessions. Supports search, ingest (two-tool flow), conflict resolution, and health checks via kirograph_wiki_* tools.',\n false,\n );\n\n if (patch.enableWiki) {\n const wikiMode = await arrowSelect<KiroGraphConfig['wikiSynthesisMode']>(\n rl,\n 'Wiki synthesis mode:',\n [\n {\n value: 'agent',\n label: 'Active agent (recommended)',\n description: 'Uses the active LLM agent to generate WIKI_DIFF blocks. Works with any AI tool. Consumes API tokens on ingest.',\n },\n {\n value: 'local',\n label: 'Local model',\n description: 'Runs a local HuggingFace model to generate diffs. Zero API cost, no data leaves your machine. Same infra as Watchmen.',\n },\n ],\n );\n patch.wikiSynthesisMode = wikiMode;\n\n if (wikiMode === 'local') {\n // \u2500\u2500 Local model selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const WIKI_LOCAL_MODELS = [\n {\n value: 'onnx-community/gemma-4-E4B-it-ONNX',\n label: 'Gemma 4 E4B (recommended)',\n description: '~3\u20134 GB \u00B7 Google DeepMind Gemma 4 \u00B7 4.5B params \u00B7 128K context \u00B7 Best quality \u00B7 Apache 2.0',\n },\n {\n value: 'onnx-community/Qwen2.5-1.5B-Instruct',\n label: 'Qwen2.5-1.5B',\n description: '~1.5 GB \u00B7 Lighter option if RAM is limited \u00B7 Acceptable quality',\n },\n {\n value: 'HuggingFaceTB/SmolLM2-1.7B-Instruct',\n label: 'SmolLM2-1.7B',\n description: '~1.7 GB \u00B7 HuggingFace compact model \u00B7 Good at following structured formats',\n },\n {\n value: '__other__',\n label: 'Other',\n description: 'Enter a custom HuggingFace model ID (must have ONNX weights on onnx-community)',\n },\n ] as const;\n\n const wikiModelChoice = await arrowSelect<string>(rl, 'Local wiki synthesis model:', WIKI_LOCAL_MODELS.map(m => ({ value: m.value, label: m.label, description: m.description })));\n\n if (wikiModelChoice === '__other__') {\n console.log(`\\n ${dim}Enter a HuggingFace model ID (e.g. onnx-community/gemma-4-E4B-it-ONNX).${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Model identifier:${reset} `)).trim();\n if (raw.includes('/')) { patch.wikiLocalModel = raw; break; }\n console.log(` Expected a HuggingFace model ID in the format org/model-name.`);\n }\n } else {\n patch.wikiLocalModel = wikiModelChoice;\n }\n }\n }\n\n return { patch, hooksToImport };\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["/**\n * KiroGraph Installer \u2014 configuration prompting\n */\n\nimport * as readline from 'readline';\nimport { KiroGraphConfig } from '../../config';\ntype CavemanMode = 'lite' | 'full' | 'ultra';\nimport { ask, askToggle, arrowSelect, printSection, printSeparator, dim, reset, violet } from './prompts';\nimport { promptImportGlobalHookSelection } from '../../hooks/import-prompt';\n\nexport interface PromptConfigOptions {\n projectRoot?: string;\n offerHookImport?: boolean;\n}\nexport type ConfigPatch = Pick<KiroGraphConfig,\n 'enableEmbeddings' | 'useVecIndex' | 'semanticEngine' |\n 'turboquantMemDocs' | 'turboquantBits' | 'turbovecMemDocs' | 'turbovecBits' |\n 'typesenseDashboard' | 'qdrantDashboard' |\n 'extractDocstrings' | 'trackCallSites' | 'enableArchitecture' |\n 'cavemanMode' | 'shellCompressionLevel' |\n 'enableMemory' | 'enableWatchmen' | 'watchmenThreshold' | 'watchmenSynthesisMode' | 'watchmenLocalModel' |\n 'enableDocs' | 'docsContextLimit' |\n 'enableData' | 'dataContextLimit' |\n 'enableSecurity' | 'enablePatterns' |\n 'enableWiki' | 'wikiSynthesisMode' | 'wikiLocalModel' |\n 'enableCodeHealth' | 'enableNavigation' | 'enableComplexity' |\n 'enableGitContext' | 'enableEditPrimitives' | 'enableBranch' |\n 'enableAgentUtils' | 'enableGeneralCompression' |\n 'memoryRelationMode' | 'wikiContradictionMode' | 'securityAuthDetectionMode'\n> & { embeddingModel?: string; embeddingDim?: number };\nexport type SemanticEngine = KiroGraphConfig['semanticEngine'];\n\ntype InstallMode = 'core' | 'full' | 'custom' | 'profiles';\n\nconst PROFILES: Record<string, { label: string; description: string; patch: Partial<ConfigPatch> }> = {\n developer: {\n label: 'Developer',\n description: 'Code health, navigation, complexity, call-site tracking',\n patch: { enableCodeHealth: true, enableNavigation: true, enableComplexity: true, trackCallSites: true },\n },\n team: {\n label: 'Team',\n description: 'Developer + architecture, git context, wiki',\n patch: { enableCodeHealth: true, enableNavigation: true, enableComplexity: true, trackCallSites: true, enableArchitecture: true, enableGitContext: true, enableWiki: true, wikiSynthesisMode: 'agent' },\n },\n security: {\n label: 'Security',\n description: 'Security analysis, patterns, architecture, code health',\n patch: { enableSecurity: true, enableArchitecture: true, enablePatterns: true, enableCodeHealth: true },\n },\n data: {\n label: 'Data & Docs',\n description: 'Tabular data indexing and documentation navigation',\n patch: { enableData: true, enableDocs: true },\n },\n ai: {\n label: 'AI / LLM Agent',\n description: 'Memory, watchmen, agent utils, wiki, general compression',\n patch: { enableMemory: true, enableWatchmen: true, enableAgentUtils: true, enableWiki: true, wikiSynthesisMode: 'agent', enableGeneralCompression: true },\n },\n};\n\nexport const DEFAULT_EMBEDDING_MODEL = 'nomic-ai/nomic-embed-text-v1.5';\n\n/** Well-known embedding models with their output dimensions. */\nconst PRESET_MODELS = [\n {\n value: 'nomic-ai/nomic-embed-text-v1.5',\n label: 'nomic-embed-text-v1.5',\n dim: 768,\n description: '768-dim \u00B7 ~130MB \u00B7 Best quality for code search (recommended)',\n },\n {\n value: 'onnx-community/embeddinggemma-300m-ONNX',\n label: 'embeddinggemma-300m',\n dim: 768,\n description: '768-dim \u00B7 ~300MB \u00B7 Google Gemma-based, multilingual, 2048-token context',\n },\n {\n value: 'Xenova/all-MiniLM-L6-v2',\n label: 'all-MiniLM-L6-v2',\n dim: 384,\n description: '384-dim \u00B7 ~23MB \u00B7 Fast and lightweight, lower accuracy',\n },\n {\n value: 'BAAI/bge-base-en-v1.5',\n label: 'bge-base-en-v1.5',\n dim: 768,\n description: '768-dim \u00B7 ~110MB \u00B7 Strong general-purpose alternative to nomic',\n },\n {\n value: '__other__',\n label: 'Other',\n dim: 768,\n description: 'Enter a custom HuggingFace model ID and embedding dimension',\n },\n] as const;\n\ntype EmbeddingPatch = Pick<ConfigPatch,\n 'enableEmbeddings' | 'embeddingModel' | 'embeddingDim' | 'semanticEngine' | 'useVecIndex' |\n 'turboquantMemDocs' | 'turboquantBits' | 'turbovecMemDocs' | 'turbovecBits' |\n 'typesenseDashboard' | 'qdrantDashboard'\n>;\n\n/**\n * Semantic embeddings are a core feature, not a \"custom\"-only extra \u2014 asked\n * for every install mode (core, full, profiles, custom) so users always get\n * to pick whether embeddings run and, if so, which model/engine.\n */\nasync function promptEmbeddings(rl: readline.Interface): Promise<EmbeddingPatch> {\n printSection('\uD83D\uDD0D', 'Semantic Search');\n\n const enableEmbeddings = await askToggle(\n rl,\n 'Semantic embeddings (similarity search):',\n 'Enables natural-language code search via vector embeddings. A local model (~130MB) is downloaded on first use.',\n );\n\n const patch: EmbeddingPatch = {\n enableEmbeddings,\n semanticEngine: 'cosine',\n useVecIndex: false,\n turboquantMemDocs: false, turboquantBits: 3,\n turbovecMemDocs: false, turbovecBits: 4,\n typesenseDashboard: false, qdrantDashboard: false,\n };\n\n if (!enableEmbeddings) {\n return patch;\n }\n\n // \u2500\u2500 Model selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const modelChoice = await arrowSelect<string>(\n rl,\n 'Embedding model:',\n PRESET_MODELS.map(m => ({ value: m.value, label: m.label, description: m.description })),\n );\n\n let embeddingModel: string;\n let embeddingDim: number;\n\n if (modelChoice === '__other__') {\n console.log(`\\n ${dim}Enter a HuggingFace model ID in the format org/model-name.${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Model identifier:${reset} `)).trim();\n if (raw.includes('/')) { embeddingModel = raw; break; }\n console.log(` Expected a HuggingFace model ID in the format org/model-name (e.g. nomic-ai/nomic-embed-text-v1.5).`);\n }\n console.log(`\\n ${dim}Enter the embedding output dimension for this model (check the model card on HuggingFace).${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Embedding dimension (e.g. 768, 384):${reset} `)).trim();\n const n = parseInt(raw, 10);\n if (!isNaN(n) && n > 0) { embeddingDim = n; break; }\n console.log(` Expected a positive integer (e.g. 768, 384, 1536).`);\n }\n } else {\n const preset = PRESET_MODELS.find(m => m.value === modelChoice)!;\n embeddingModel = preset.value;\n embeddingDim = preset.dim;\n }\n\n patch.embeddingModel = embeddingModel;\n patch.embeddingDim = embeddingDim;\n\n // \u2500\u2500 Engine selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const semanticEngine = await arrowSelect<SemanticEngine>(rl, 'Vector search engine:', [\n { value: 'cosine', label: 'cosine', description: 'In-process cosine similarity. No extra deps. Best for small/medium projects.' },\n { value: 'turboquant', label: 'turboquant', description: 'ANN index, zero native deps. Compresses embeddings 20\u201330\u00D7 (Google TurboQuant). ANN without native binaries \u2014 ideal for CI, ARM, restricted envs. Optional: npm install turboquant-js.' },\n { value: 'turbovec', label: 'turbovec', description: 'ANN search via Rust/SIMD (napi-rs). Same TurboQuant algorithm but NEON on ARM and AVX-512BW on x86 \u2014 faster than turboquant-js at the cost of a one-time Rust build. Requires Rust toolchain. Build: cd native/turbovec-node && npm install && npm run build.' },\n { value: 'sqlite-vec', label: 'sqlite-vec', description: 'ANN index. Sub-linear search. Best for large codebases. Needs: better-sqlite3, sqlite-vec (native).' },\n { value: 'orama', label: 'orama', description: 'Hybrid search (full-text + vector). Pure JS. Needs: @orama/orama, @orama/plugin-data-persistence.' },\n { value: 'pglite', label: 'pglite', description: 'Hybrid search via PostgreSQL + pgvector. Exact results. Pure WASM. Needs: @electric-sql/pglite.' },\n { value: 'lancedb', label: 'lancedb', description: 'ANN search via LanceDB (Apache Lance columnar format). Pure JS. Needs: @lancedb/lancedb.' },\n { value: 'qdrant', label: 'qdrant', description: 'ANN search via Qdrant embedded binary (HNSW index, Cosine). Needs: qdrant-local.' },\n { value: 'typesense', label: 'typesense', description: 'ANN search via Typesense (auto-downloaded binary, HNSW, Cosine). Needs: typesense.' },\n ]);\n patch.semanticEngine = semanticEngine;\n patch.useVecIndex = semanticEngine === 'sqlite-vec';\n\n // TurboQuant for memory & docs: offer only when turboquant is the code-node engine\n if (semanticEngine === 'turboquant') {\n patch.turboquantMemDocs = await askToggle(rl,\n 'TurboQuant for memory & docs search (optional):',\n 'Replaces the default linear cosine scan in memory observations and doc sections with a compressed ANN index \u2014 no native deps required. Most useful when you accumulate many observations or large doc sets (1 000+ entries).',\n false,\n );\n }\n\n // TurboVec bit width\n if (semanticEngine === 'turbovec') {\n patch.turbovecBits = await arrowSelect<number>(rl, 'TurboVec bits per coordinate:', [\n { value: 4, label: '4 bits (recommended)', description: 'Best quality, ~19\u00D7 compression vs raw Float32. Default.' },\n { value: 3, label: '3 bits', description: 'Balanced \u2014 ~25\u00D7 compression, slight quality drop.' },\n { value: 2, label: '2 bits', description: 'Highest compression (~38\u00D7), lowest accuracy.' },\n ]);\n patch.turbovecMemDocs = await askToggle(rl,\n 'TurboVec for memory & docs search (optional):',\n 'Replaces the default linear cosine scan in memory observations and doc sections with the TurboVec ANN index. Requires the addon to be built.',\n false,\n );\n }\n\n if (semanticEngine === 'typesense') {\n patch.typesenseDashboard = await askToggle(rl,\n 'Typesense dashboard:',\n 'Serves the Typesense Dashboard locally and opens it in your browser after indexing completes.',\n false,\n );\n }\n\n if (semanticEngine === 'qdrant') {\n patch.qdrantDashboard = await askToggle(rl,\n 'Qdrant dashboard:',\n 'Downloads the Qdrant Web UI (first time only) and opens it in your browser after indexing completes.',\n false,\n );\n }\n\n return patch;\n}\n\n/**\n * jev (TypeSafe System One, https://docs.typesafe.ai) is an opt-in typed-\n * classification backend for three otherwise-independent features. It only\n * makes sense to ask about it once the modules it attaches to are known, and\n * only when at least one of them is actually enabled \u2014 there's nothing for\n * it to classify otherwise. Mutates `patch` in place.\n */\nasync function promptJevClassification(rl: readline.Interface, patch: ConfigPatch): Promise<void> {\n const targets: string[] = [];\n if (patch.enableMemory) targets.push('memory relation judging');\n if (patch.enableWiki) targets.push('wiki contradiction detection');\n if (patch.enableSecurity) targets.push('attack-surface auth detection');\n if (targets.length === 0) return;\n\n printSection('\uD83E\uDDEA', 'jev Classification (experimental)');\n\n const enableJev = await askToggle(\n rl,\n `jev-powered classification for: ${targets.join(', ')}?`,\n '\u26A0 Experimental. jev (TypeSafe System One, https://docs.typesafe.ai) is a fast typed-classification model that replaces a heuristic or agent-reasoning step with a real judgment call for each of the modules above. Requires a paid third-party API key \u2014 a .kirograph/.env file will be created for you to add JEV_API_KEY after install. Falls back to each module\\'s existing non-jev behavior whenever the key is unset.',\n false,\n );\n if (!enableJev) return;\n\n if (patch.enableMemory) patch.memoryRelationMode = 'jev';\n if (patch.enableWiki) patch.wikiContradictionMode = 'jev';\n if (patch.enableSecurity) patch.securityAuthDetectionMode = 'jev';\n}\n\nexport async function promptConfigOptions(\n rl: readline.Interface,\n opts: PromptConfigOptions = {},\n): Promise<{ patch: ConfigPatch; hooksToImport: string[] | null }> {\n // \u2500\u2500 Install mode \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const installMode = await arrowSelect<InstallMode>(rl, 'Installation mode:', [\n { value: 'core', label: 'Core only', description: '3 always-on tools (search, context, node) \u2014 ~170 tok. Zero config.' },\n { value: 'full', label: 'Full', description: 'Enable every feature with sensible defaults. Best for a fresh project.' },\n { value: 'profiles', label: 'Profiles', description: 'Choose a preset bundle (Developer, Team, Security, Data & Docs, AI/LLM).' },\n { value: 'custom', label: 'Custom', description: 'Answer each question individually. Maximum control.' },\n ]);\n\n const basePatch: ConfigPatch = {\n enableEmbeddings: false, useVecIndex: false, semanticEngine: 'cosine',\n turboquantMemDocs: false, turboquantBits: 3, turbovecMemDocs: false, turbovecBits: 4,\n typesenseDashboard: false, qdrantDashboard: false,\n extractDocstrings: false, trackCallSites: false,\n enableArchitecture: false, cavemanMode: 'off', shellCompressionLevel: 'off',\n enableMemory: false, enableWatchmen: false, watchmenThreshold: 5,\n watchmenSynthesisMode: 'local', watchmenLocalModel: 'onnx-community/gemma-4-E4B-it-ONNX',\n enableDocs: false, docsContextLimit: 0,\n enableData: false, dataContextLimit: 0,\n enableSecurity: false, enablePatterns: false,\n enableWiki: false, wikiSynthesisMode: 'agent', wikiLocalModel: 'onnx-community/gemma-4-E4B-it-ONNX',\n enableCodeHealth: false, enableNavigation: false, enableComplexity: false,\n enableGitContext: false, enableEditPrimitives: false, enableBranch: false,\n enableAgentUtils: false, enableGeneralCompression: false,\n memoryRelationMode: 'agent', wikiContradictionMode: 'heuristic', securityAuthDetectionMode: 'heuristic',\n };\n\n if (installMode === 'core') {\n const embeddingPatch = await promptEmbeddings(rl);\n return { patch: { ...basePatch, ...embeddingPatch }, hooksToImport: null };\n }\n\n if (installMode === 'full') {\n const embeddingPatch = await promptEmbeddings(rl);\n const fullPatch: ConfigPatch = {\n ...basePatch,\n ...embeddingPatch,\n extractDocstrings: true, trackCallSites: true,\n enableArchitecture: true, shellCompressionLevel: 'normal',\n enableCodeHealth: true, enableNavigation: true, enableComplexity: true,\n enableGitContext: true, enableEditPrimitives: true, enableBranch: true,\n enableAgentUtils: true, enableGeneralCompression: true,\n enableSecurity: true, enablePatterns: true,\n enableDocs: true, enableData: true,\n enableMemory: true, enableWatchmen: true,\n enableWiki: true, wikiSynthesisMode: 'agent',\n };\n await promptJevClassification(rl, fullPatch);\n return { patch: fullPatch, hooksToImport: null };\n }\n\n if (installMode === 'profiles') {\n const profileKey = await arrowSelect<string>(rl, 'Select a profile:', Object.entries(PROFILES).map(([key, p]) => ({\n value: key,\n label: p.label,\n description: p.description,\n })));\n const profile = PROFILES[profileKey];\n const embeddingPatch = await promptEmbeddings(rl);\n const patch: ConfigPatch = { ...basePatch, ...profile.patch, ...embeddingPatch };\n await promptJevClassification(rl, patch);\n return { patch, hooksToImport: null };\n }\n\n // \u2500\u2500 Custom: ask all questions individually \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const embeddingPatch = await promptEmbeddings(rl);\n const patch: ConfigPatch = { ...basePatch, ...embeddingPatch };\n\n // \u2500\u2500 Graph Features \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCCA', 'Graph Features');\n\n patch.extractDocstrings = await askToggle(rl,\n 'Docstring extraction:',\n 'Enriches symbol metadata and improves context quality. Slightly increases indexing time.',\n false,\n );\n\n patch.trackCallSites = await askToggle(rl,\n 'Call site tracking (caller/callee graph):',\n 'Enables kirograph_callers and kirograph_callees MCP tools. Increases index size.',\n false,\n );\n\n patch.enableArchitecture = await askToggle(rl,\n 'Architecture analysis (packages + layers):',\n 'Detects packages from manifests and architectural layers. Enables kirograph_architecture, kirograph_coupling, kirograph_package.',\n false,\n );\n\n // \u2500\u2500 Graph Tools \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCCA', 'Graph Tools');\n\n patch.enableNavigation = await askToggle(rl,\n 'Navigation tools (status, files, impact):',\n 'Enables kirograph_status, kirograph_files, kirograph_impact.',\n false,\n );\n\n patch.enableCodeHealth = await askToggle(rl,\n 'Code health tools (hotspots, dead code, path analysis, type hierarchy):',\n 'Enables kirograph_hotspots, kirograph_surprising, kirograph_diff, kirograph_dead_code, kirograph_circular_deps, kirograph_path, kirograph_affected, kirograph_type_hierarchy.',\n false,\n );\n\n patch.enableComplexity = await askToggle(rl,\n 'Complexity metrics tools:',\n 'Enables complexity analysis, simplify scan, health score, DSM, test risk.',\n false,\n );\n\n patch.enableGitContext = await askToggle(rl,\n 'Git context tools (diff context, commit context, flows):',\n 'Enables kirograph_flows, kirograph_diff_context, kirograph_commit_context, kirograph_pr_context, kirograph_changelog, kirograph_test_map, kirograph_test_coverage.',\n false,\n );\n\n patch.enableEditPrimitives = await askToggle(rl,\n 'Edit primitive tools (str_replace, insert_at, refactor):',\n 'Enables kirograph_refactor, kirograph_str_replace, kirograph_multi_str_replace, kirograph_insert_at, kirograph_ast_grep_rewrite.',\n false,\n );\n\n patch.enableAgentUtils = await askToggle(rl,\n 'Agent utilities (file caching, budget tracking):',\n 'Enables kirograph_read, kirograph_gain, kirograph_budget.',\n false,\n );\n\n // \u2500\u2500 Security \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDD12', 'Security');\n\n patch.enableSecurity = await askToggle(rl,\n 'Security analysis (vulnerability scanning + reachability):',\n 'Scans dependency manifests for known vulnerabilities and performs reachability analysis. Requires Architecture analysis (will be auto-enabled). Enables kirograph_security, kirograph_vulns, kirograph_sbom, kirograph_vex, kirograph_reachability MCP tools.',\n false,\n );\n\n if (patch.enableSecurity && !patch.enableArchitecture) {\n patch.enableArchitecture = true;\n console.log(' \u2139 Architecture analysis auto-enabled (required by Security module)');\n }\n\n // \u2500\u2500 Pattern Matching \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDD0D', 'Pattern Matching');\n\n patch.enablePatterns = await askToggle(rl,\n 'Precise SAST with ast-grep?',\n 'Runs AST structural pattern matching during indexing using @ast-grep/napi (~15MB native binding). Unlike heuristic symbol-name analysis, matches real code structure \u2014 precise SQL injection, path traversal, eval detection. Requires @ast-grep/napi (will be installed automatically if you answer yes).',\n false,\n );\n\n // \u2500\u2500 Documentation \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCD6', 'Documentation');\n\n (patch as any).enableDocs = await askToggle(rl,\n 'Documentation indexing (section-level retrieval):',\n 'Indexes docs by heading structure. Enables kirograph_docs_toc, kirograph_docs_search, kirograph_docs_section, kirograph_docs_outline, kirograph_docs_refs.',\n false,\n );\n\n if ((patch as any).enableDocs) {\n const contextChoice = await arrowSelect<number>(rl, 'Include doc sections in kirograph_context results?', [\n { value: 0, label: '0 (disabled)', description: 'Docs stay separate \u2014 use kirograph_docs_* tools explicitly (recommended)' },\n { value: 3, label: '3 sections', description: 'Include up to 3 relevant doc sections in context results' },\n { value: 5, label: '5 sections', description: 'Include up to 5 relevant doc sections in context results' },\n { value: 10, label: '10 sections', description: 'Include up to 10 relevant doc sections in context results' },\n ]);\n (patch as any).docsContextLimit = contextChoice;\n }\n\n // \u2500\u2500 Data \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCCA', 'Data');\n\n (patch as any).enableData = await askToggle(rl,\n 'Tabular data indexing (CSV/TSV/JSONL/JSON/Excel/Parquet):',\n 'Indexes data files for structured querying. Enables kirograph_data_list, kirograph_data_describe, kirograph_data_query, kirograph_data_aggregate, kirograph_data_search.',\n false,\n );\n\n if ((patch as any).enableData) {\n (patch as any).dataInstallExcel = await askToggle(rl,\n 'Install Excel support (xlsx package)?',\n 'Required for .xlsx/.xls files. CSV/TSV/JSONL/JSON are always supported without extra deps.',\n false,\n );\n\n (patch as any).dataInstallParquet = await askToggle(rl,\n 'Install Parquet support (parquetjs-lite package)?',\n 'Required for .parquet files. CSV/TSV/JSONL/JSON are always supported without extra deps.',\n false,\n );\n\n (patch as any).dataInstallPdf = await askToggle(rl,\n 'Install PDF support (@firecrawl/pdf-inspector package)?',\n 'Required for .pdf files. Rust/NAPI binary \u2014 prebuilts for linux-x64 and macOS ARM64.',\n false,\n );\n\n const contextChoice = await arrowSelect<number>(rl, 'Include dataset schemas in kirograph_context results?', [\n { value: 0, label: '0 (disabled)', description: 'Data stays separate \u2014 use kirograph_data_* tools explicitly (recommended)' },\n { value: 2, label: '2 datasets', description: 'Include up to 2 relevant dataset schemas in context results' },\n { value: 5, label: '5 datasets', description: 'Include up to 5 relevant dataset schemas in context results' },\n ]);\n (patch as any).dataContextLimit = contextChoice;\n }\n\n // \u2500\u2500 Agent Behavior \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83E\uDD16', 'Agent Behavior');\n\n const cavemanChoice = await arrowSelect(rl, 'Communication style (caveman mode):', [\n { value: 'off', label: 'off', description: 'Normal responses \u2014 no compression' },\n { value: 'lite', label: 'lite', description: 'Compact, no filler, full sentences' },\n { value: 'full', label: 'full', description: 'Fragments, no articles, short synonyms' },\n { value: 'ultra', label: 'ultra', description: 'Max compression, abbreviations, \u2192 for causality' },\n ]);\n patch.cavemanMode = cavemanChoice as CavemanMode | 'off';\n\n const compressionChoice = await arrowSelect(rl, 'Shell compression (kirograph_exec):', [\n { value: 'off', label: 'off', description: 'Disables kirograph_exec entirely' },\n { value: 'normal', label: 'normal', description: 'Balanced: removes noise, keeps structure (recommended)' },\n { value: 'aggressive', label: 'aggressive', description: 'More compact: groups by category, limits output' },\n { value: 'ultra', label: 'ultra', description: 'Maximum compression: counts and summaries only' },\n ]);\n patch.shellCompressionLevel = compressionChoice as KiroGraphConfig['shellCompressionLevel'];\n if (compressionChoice === 'off') {\n console.log(' \u2139 kirograph_exec disabled (shell compression is off)');\n }\n\n patch.enableGeneralCompression = await askToggle(rl,\n 'General-purpose compression tool (kirograph_compress):',\n 'Enables kirograph_compress \u2014 an on-demand MCP tool that compresses arbitrary text before it reaches the model. ' +\n 'Two engines: rtk-style structural filters for shell output (git, npm, test logs) when a command hint is provided, ' +\n 'or caveman grammar rules for prose and observations otherwise. ' +\n 'Useful when the agent pastes large content, receives a fat RAG chunk, or wants to explicitly compress before storing. ' +\n 'Independent from automatic shell compression (kirograph_exec) and caveman mode \u2014 those apply in the background; ' +\n 'this gives the model an explicit, on-demand compression action.',\n false,\n );\n\n let hooksToImport: string[] | null = null;\n if (opts.offerHookImport && opts.projectRoot) {\n printSection('\uD83E\uDE9D', 'Hooks');\n hooksToImport = await promptImportGlobalHookSelection();\n }\n\n // \u2500\u2500 Memory \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83E\uDDE0', 'Memory');\n\n patch.enableMemory = await askToggle(rl,\n 'Persistent memory (cross-session observations):',\n 'Stores decisions, errors, and patterns across sessions. Compressed (if caveman is on), linked to code symbols, searchable via kirograph_mem_* tools. Zero LLM tokens on write.',\n false,\n );\n\n if (patch.enableMemory) {\n patch.enableWatchmen = await askToggle(rl,\n 'Watchmen (auto-synthesize workspace briefs from memory):',\n 'When enough observations accumulate (default: 5), synthesizes them into .kiro/steering/kirograph-watchmen.md, CLAUDE.md, AGENTS.md, or the equivalent for your tool.',\n false,\n );\n\n if (patch.enableWatchmen) {\n // \u2500\u2500 Synthesis mode \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const synthesisMode = await arrowSelect<KiroGraphConfig['watchmenSynthesisMode']>(\n rl,\n 'Watchmen synthesis mode:',\n [\n {\n value: 'local',\n label: 'Local model',\n description: 'Runs a local HuggingFace model via @huggingface/transformers. Zero API cost, no data leaves your machine. Model downloaded once to ~/.kirograph/models/. Works for all tools via runCommand hook.',\n },\n {\n value: 'agent',\n label: 'Active agent',\n description: '\u26A0 Kiro only. Uses the active Kiro agent to synthesize. Consumes API tokens/credits on every synthesis. Not supported for other tools.',\n },\n ],\n );\n patch.watchmenSynthesisMode = synthesisMode;\n\n if (synthesisMode === 'local') {\n // \u2500\u2500 Local model selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const LOCAL_MODELS = [\n {\n value: 'onnx-community/gemma-4-E4B-it-ONNX',\n label: 'Gemma 4 E4B (recommended)',\n description: '~3\u20134 GB \u00B7 Google DeepMind Gemma 4 \u00B7 4.5B params \u00B7 128K context \u00B7 Best quality \u00B7 Apache 2.0',\n },\n {\n value: 'onnx-community/Qwen2.5-1.5B-Instruct',\n label: 'Qwen2.5-1.5B',\n description: '~1.5 GB \u00B7 Lighter option if RAM is limited \u00B7 Acceptable quality',\n },\n {\n value: 'HuggingFaceTB/SmolLM2-1.7B-Instruct',\n label: 'SmolLM2-1.7B',\n description: '~1.7 GB \u00B7 HuggingFace compact model \u00B7 Good at following structured formats',\n },\n {\n value: '__other__',\n label: 'Other',\n description: 'Enter a custom HuggingFace model ID (must have ONNX weights on onnx-community)',\n },\n ] as const;\n\n const modelChoice = await arrowSelect<string>(rl, 'Local synthesis model:', LOCAL_MODELS.map(m => ({ value: m.value, label: m.label, description: m.description })));\n\n if (modelChoice === '__other__') {\n console.log(`\\n ${dim}Enter a HuggingFace model ID (e.g. onnx-community/gemma-4-E4B-it-ONNX).${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Model identifier:${reset} `)).trim();\n if (raw.includes('/')) { patch.watchmenLocalModel = raw; break; }\n console.log(` Expected a HuggingFace model ID in the format org/model-name.`);\n }\n } else {\n patch.watchmenLocalModel = modelChoice;\n }\n }\n }\n }\n\n // \u2500\u2500 Wiki \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n printSection('\uD83D\uDCD6', 'Wiki');\n\n patch.enableWiki = await askToggle(rl,\n 'LLM Wiki (Karpathy-style structured knowledge base):',\n 'Maintains a set of markdown pages that compound knowledge across sessions. Supports search, ingest (two-tool flow), conflict resolution, and health checks via kirograph_wiki_* tools.',\n false,\n );\n\n if (patch.enableWiki) {\n const wikiMode = await arrowSelect<KiroGraphConfig['wikiSynthesisMode']>(\n rl,\n 'Wiki synthesis mode:',\n [\n {\n value: 'agent',\n label: 'Active agent (recommended)',\n description: 'Uses the active LLM agent to generate WIKI_DIFF blocks. Works with any AI tool. Consumes API tokens on ingest.',\n },\n {\n value: 'local',\n label: 'Local model',\n description: 'Runs a local HuggingFace model to generate diffs. Zero API cost, no data leaves your machine. Same infra as Watchmen.',\n },\n ],\n );\n patch.wikiSynthesisMode = wikiMode;\n\n if (wikiMode === 'local') {\n // \u2500\u2500 Local model selection \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n const WIKI_LOCAL_MODELS = [\n {\n value: 'onnx-community/gemma-4-E4B-it-ONNX',\n label: 'Gemma 4 E4B (recommended)',\n description: '~3\u20134 GB \u00B7 Google DeepMind Gemma 4 \u00B7 4.5B params \u00B7 128K context \u00B7 Best quality \u00B7 Apache 2.0',\n },\n {\n value: 'onnx-community/Qwen2.5-1.5B-Instruct',\n label: 'Qwen2.5-1.5B',\n description: '~1.5 GB \u00B7 Lighter option if RAM is limited \u00B7 Acceptable quality',\n },\n {\n value: 'HuggingFaceTB/SmolLM2-1.7B-Instruct',\n label: 'SmolLM2-1.7B',\n description: '~1.7 GB \u00B7 HuggingFace compact model \u00B7 Good at following structured formats',\n },\n {\n value: '__other__',\n label: 'Other',\n description: 'Enter a custom HuggingFace model ID (must have ONNX weights on onnx-community)',\n },\n ] as const;\n\n const wikiModelChoice = await arrowSelect<string>(rl, 'Local wiki synthesis model:', WIKI_LOCAL_MODELS.map(m => ({ value: m.value, label: m.label, description: m.description })));\n\n if (wikiModelChoice === '__other__') {\n console.log(`\\n ${dim}Enter a HuggingFace model ID (e.g. onnx-community/gemma-4-E4B-it-ONNX).${reset}`);\n while (true) {\n const raw = (await ask(rl, ` ${violet}Model identifier:${reset} `)).trim();\n if (raw.includes('/')) { patch.wikiLocalModel = raw; break; }\n console.log(` Expected a HuggingFace model ID in the format org/model-name.`);\n }\n } else {\n patch.wikiLocalModel = wikiModelChoice;\n }\n }\n }\n\n await promptJevClassification(rl, patch);\n\n return { patch, hooksToImport };\n}\n"],
5
+ "mappings": "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",
6
6
  "names": ["embeddingPatch", "patch"]
7
7
  }