@hiveai/core 0.2.11 → 0.2.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +18 -6
- package/dist/index.js +13 -5
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -2,7 +2,7 @@ import { z } from 'zod';
|
|
|
2
2
|
|
|
3
3
|
declare const MemoryScopeSchema: z.ZodEnum<["personal", "team", "module"]>;
|
|
4
4
|
declare const MemoryStatusSchema: z.ZodEnum<["draft", "proposed", "validated", "deprecated", "stale", "rejected"]>;
|
|
5
|
-
declare const MemoryTypeSchema: z.ZodEnum<["convention", "decision", "gotcha", "architecture", "glossary", "attempt"]>;
|
|
5
|
+
declare const MemoryTypeSchema: z.ZodEnum<["convention", "decision", "gotcha", "architecture", "glossary", "attempt", "session_recap"]>;
|
|
6
6
|
declare const AnchorSchema: z.ZodObject<{
|
|
7
7
|
commit: z.ZodOptional<z.ZodString>;
|
|
8
8
|
paths: z.ZodDefault<z.ZodArray<z.ZodString, "many">>;
|
|
@@ -20,7 +20,7 @@ declare const MemoryFrontmatterSchema: z.ZodEffects<z.ZodObject<{
|
|
|
20
20
|
id: z.ZodString;
|
|
21
21
|
scope: z.ZodDefault<z.ZodEnum<["personal", "team", "module"]>>;
|
|
22
22
|
module: z.ZodOptional<z.ZodString>;
|
|
23
|
-
type: z.ZodEnum<["convention", "decision", "gotcha", "architecture", "glossary", "attempt"]>;
|
|
23
|
+
type: z.ZodEnum<["convention", "decision", "gotcha", "architecture", "glossary", "attempt", "session_recap"]>;
|
|
24
24
|
status: z.ZodDefault<z.ZodEnum<["draft", "proposed", "validated", "deprecated", "stale", "rejected"]>>;
|
|
25
25
|
anchor: z.ZodDefault<z.ZodObject<{
|
|
26
26
|
commit: z.ZodOptional<z.ZodString>;
|
|
@@ -44,8 +44,10 @@ declare const MemoryFrontmatterSchema: z.ZodEffects<z.ZodObject<{
|
|
|
44
44
|
stale_reason: z.ZodDefault<z.ZodNullable<z.ZodString>>;
|
|
45
45
|
related_ids: z.ZodDefault<z.ZodArray<z.ZodString, "many">>;
|
|
46
46
|
last_read_at: z.ZodDefault<z.ZodNullable<z.ZodString>>;
|
|
47
|
+
topic: z.ZodOptional<z.ZodString>;
|
|
48
|
+
revision_count: z.ZodDefault<z.ZodNumber>;
|
|
47
49
|
}, "strip", z.ZodTypeAny, {
|
|
48
|
-
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt";
|
|
50
|
+
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt" | "session_recap";
|
|
49
51
|
status: "draft" | "proposed" | "validated" | "deprecated" | "stale" | "rejected";
|
|
50
52
|
id: string;
|
|
51
53
|
scope: "personal" | "team" | "module";
|
|
@@ -61,11 +63,13 @@ declare const MemoryFrontmatterSchema: z.ZodEffects<z.ZodObject<{
|
|
|
61
63
|
stale_reason: string | null;
|
|
62
64
|
related_ids: string[];
|
|
63
65
|
last_read_at: string | null;
|
|
66
|
+
revision_count: number;
|
|
64
67
|
module?: string | undefined;
|
|
65
68
|
domain?: string | undefined;
|
|
66
69
|
author?: string | undefined;
|
|
70
|
+
topic?: string | undefined;
|
|
67
71
|
}, {
|
|
68
|
-
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt";
|
|
72
|
+
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt" | "session_recap";
|
|
69
73
|
id: string;
|
|
70
74
|
created_at: string | Date;
|
|
71
75
|
module?: string | undefined;
|
|
@@ -84,8 +88,10 @@ declare const MemoryFrontmatterSchema: z.ZodEffects<z.ZodObject<{
|
|
|
84
88
|
stale_reason?: string | null | undefined;
|
|
85
89
|
related_ids?: string[] | undefined;
|
|
86
90
|
last_read_at?: string | null | undefined;
|
|
91
|
+
topic?: string | undefined;
|
|
92
|
+
revision_count?: number | undefined;
|
|
87
93
|
}>, {
|
|
88
|
-
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt";
|
|
94
|
+
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt" | "session_recap";
|
|
89
95
|
status: "draft" | "proposed" | "validated" | "deprecated" | "stale" | "rejected";
|
|
90
96
|
id: string;
|
|
91
97
|
scope: "personal" | "team" | "module";
|
|
@@ -101,11 +107,13 @@ declare const MemoryFrontmatterSchema: z.ZodEffects<z.ZodObject<{
|
|
|
101
107
|
stale_reason: string | null;
|
|
102
108
|
related_ids: string[];
|
|
103
109
|
last_read_at: string | null;
|
|
110
|
+
revision_count: number;
|
|
104
111
|
module?: string | undefined;
|
|
105
112
|
domain?: string | undefined;
|
|
106
113
|
author?: string | undefined;
|
|
114
|
+
topic?: string | undefined;
|
|
107
115
|
}, {
|
|
108
|
-
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt";
|
|
116
|
+
type: "convention" | "decision" | "gotcha" | "architecture" | "glossary" | "attempt" | "session_recap";
|
|
109
117
|
id: string;
|
|
110
118
|
created_at: string | Date;
|
|
111
119
|
module?: string | undefined;
|
|
@@ -124,6 +132,8 @@ declare const MemoryFrontmatterSchema: z.ZodEffects<z.ZodObject<{
|
|
|
124
132
|
stale_reason?: string | null | undefined;
|
|
125
133
|
related_ids?: string[] | undefined;
|
|
126
134
|
last_read_at?: string | null | undefined;
|
|
135
|
+
topic?: string | undefined;
|
|
136
|
+
revision_count?: number | undefined;
|
|
127
137
|
}>;
|
|
128
138
|
|
|
129
139
|
type MemoryScope = z.infer<typeof MemoryScopeSchema>;
|
|
@@ -151,6 +161,8 @@ declare function buildFrontmatter(input: {
|
|
|
151
161
|
paths?: string[];
|
|
152
162
|
symbols?: string[];
|
|
153
163
|
commit?: string;
|
|
164
|
+
topic?: string;
|
|
165
|
+
status?: MemoryFrontmatter["status"];
|
|
154
166
|
}): MemoryFrontmatter;
|
|
155
167
|
|
|
156
168
|
declare const HAIVE_DIR = ".ai";
|
package/dist/index.js
CHANGED
|
@@ -15,8 +15,10 @@ var MemoryTypeSchema = z.enum([
|
|
|
15
15
|
"gotcha",
|
|
16
16
|
"architecture",
|
|
17
17
|
"glossary",
|
|
18
|
-
"attempt"
|
|
19
|
-
// failed approach
|
|
18
|
+
"attempt",
|
|
19
|
+
// failed approach — "tried X, failed because Y, use Z instead"
|
|
20
|
+
"session_recap"
|
|
21
|
+
// end-of-session summary: goal / accomplished / discoveries / next steps
|
|
20
22
|
]);
|
|
21
23
|
var AnchorSchema = z.object({
|
|
22
24
|
commit: z.string().optional(),
|
|
@@ -39,7 +41,11 @@ var MemoryFrontmatterSchema = z.object({
|
|
|
39
41
|
verified_at: z.string().nullable().default(null),
|
|
40
42
|
stale_reason: z.string().nullable().default(null),
|
|
41
43
|
related_ids: z.array(z.string()).default([]),
|
|
42
|
-
last_read_at: z.string().nullable().default(null)
|
|
44
|
+
last_read_at: z.string().nullable().default(null),
|
|
45
|
+
topic: z.string().optional(),
|
|
46
|
+
// stable key for upsert — same topic in same scope → update instead of create
|
|
47
|
+
revision_count: z.number().int().min(0).default(0)
|
|
48
|
+
// incremented each time a topic upsert occurs
|
|
43
49
|
}).refine(
|
|
44
50
|
(data) => data.scope !== "module" || !!data.module,
|
|
45
51
|
{ message: "module name is required when scope is 'module'", path: ["module"] }
|
|
@@ -90,7 +96,7 @@ function buildFrontmatter(input) {
|
|
|
90
96
|
scope: input.scope ?? "personal",
|
|
91
97
|
module: input.module,
|
|
92
98
|
type: input.type,
|
|
93
|
-
status: "draft",
|
|
99
|
+
status: input.status ?? "draft",
|
|
94
100
|
anchor: {
|
|
95
101
|
commit: input.commit,
|
|
96
102
|
paths: input.paths ?? [],
|
|
@@ -100,7 +106,9 @@ function buildFrontmatter(input) {
|
|
|
100
106
|
domain: input.domain,
|
|
101
107
|
author: input.author,
|
|
102
108
|
created_at: now.toISOString(),
|
|
103
|
-
expires_when: null
|
|
109
|
+
expires_when: null,
|
|
110
|
+
topic: input.topic,
|
|
111
|
+
revision_count: 0
|
|
104
112
|
});
|
|
105
113
|
}
|
|
106
114
|
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/schema.ts","../src/parser.ts","../src/paths.ts","../src/loader.ts","../src/search.ts","../src/verifier.ts","../src/usage.ts","../src/confidence.ts","../src/relevance.ts","../src/token-budget.ts","../src/code-map.ts"],"sourcesContent":["import { z } from \"zod\";\n\nexport const MemoryScopeSchema = z.enum([\"personal\", \"team\", \"module\"]);\n\nexport const MemoryStatusSchema = z.enum([\n \"draft\",\n \"proposed\",\n \"validated\",\n \"deprecated\",\n \"stale\",\n \"rejected\",\n]);\n\nexport const MemoryTypeSchema = z.enum([\n \"convention\",\n \"decision\",\n \"gotcha\",\n \"architecture\",\n \"glossary\",\n \"attempt\", // failed approach / negative knowledge — \"tried X, failed because Y, use Z instead\"\n]);\n\nexport const AnchorSchema = z.object({\n commit: z.string().optional(),\n paths: z.array(z.string()).default([]),\n symbols: z.array(z.string()).default([]),\n});\n\nconst IsoDateString = z\n .union([z.string(), z.date()])\n .transform((v) => (v instanceof Date ? v.toISOString() : v))\n .pipe(z.string().datetime());\n\nexport const MemoryFrontmatterSchema = z\n .object({\n id: z.string().min(1),\n scope: MemoryScopeSchema.default(\"personal\"),\n module: z.string().optional(),\n type: MemoryTypeSchema,\n status: MemoryStatusSchema.default(\"draft\"),\n anchor: AnchorSchema.default({ paths: [], symbols: [] }),\n tags: z.array(z.string()).default([]),\n domain: z.string().optional(),\n author: z.string().optional(),\n created_at: IsoDateString,\n expires_when: z.string().nullable().default(null),\n verified_at: z.string().nullable().default(null),\n stale_reason: z.string().nullable().default(null),\n related_ids: z.array(z.string()).default([]),\n last_read_at: z.string().nullable().default(null),\n })\n .refine(\n (data) => data.scope !== \"module\" || !!data.module,\n { message: \"module name is required when scope is 'module'\", path: [\"module\"] },\n );\n","import matter from \"gray-matter\";\nimport { MemoryFrontmatterSchema } from \"./schema.js\";\nimport type { Memory, MemoryFrontmatter } from \"./types.js\";\n\nconst PRIVATE_BLOCK_RE = /<private>[\\s\\S]*?<\\/private>/g;\n\nexport function stripPrivate(body: string): string {\n return body.replace(PRIVATE_BLOCK_RE, \"\").trimEnd();\n}\n\nexport function parseMemory(raw: string): Memory {\n const parsed = matter(raw);\n const frontmatter = MemoryFrontmatterSchema.parse(parsed.data);\n return {\n frontmatter,\n body: stripPrivate(parsed.content.trim()),\n };\n}\n\nfunction stripUndefined<T>(value: T): T {\n if (Array.isArray(value)) {\n return value.map((v) => stripUndefined(v)) as unknown as T;\n }\n if (value && typeof value === \"object\") {\n const out: Record<string, unknown> = {};\n for (const [k, v] of Object.entries(value as Record<string, unknown>)) {\n if (v === undefined) continue;\n out[k] = stripUndefined(v);\n }\n return out as T;\n }\n return value;\n}\n\nexport function serializeMemory(memory: Memory): string {\n const clean = stripUndefined(memory.frontmatter) as Record<string, unknown>;\n return matter.stringify(memory.body, clean);\n}\n\nexport function newMemoryId(type: string, slug: string, date = new Date()): string {\n const isoDate = date.toISOString().slice(0, 10);\n const safeSlug = slug\n .toLowerCase()\n .replace(/[^a-z0-9]+/g, \"-\")\n .replace(/^-|-$/g, \"\")\n .slice(0, 60);\n return `${isoDate}-${type}-${safeSlug}`;\n}\n\nexport function buildFrontmatter(input: {\n type: MemoryFrontmatter[\"type\"];\n slug: string;\n scope?: MemoryFrontmatter[\"scope\"];\n module?: string;\n tags?: string[];\n domain?: string;\n author?: string;\n paths?: string[];\n symbols?: string[];\n commit?: string;\n}): MemoryFrontmatter {\n const now = new Date();\n const id = newMemoryId(input.type, input.slug, now);\n return MemoryFrontmatterSchema.parse({\n id,\n scope: input.scope ?? \"personal\",\n module: input.module,\n type: input.type,\n status: \"draft\",\n anchor: {\n commit: input.commit,\n paths: input.paths ?? [],\n symbols: input.symbols ?? [],\n },\n tags: input.tags ?? [],\n domain: input.domain,\n author: input.author,\n created_at: now.toISOString(),\n expires_when: null,\n });\n}\n","import { existsSync } from \"node:fs\";\nimport path from \"node:path\";\n\nexport const HAIVE_DIR = \".ai\";\n\nconst ROOT_MARKERS = [\".ai\", \".git\", \"package.json\"];\n\nexport function findProjectRoot(startDir: string = process.cwd()): string {\n let current = path.resolve(startDir);\n const fsRoot = path.parse(current).root;\n while (current !== fsRoot) {\n for (const marker of ROOT_MARKERS) {\n if (existsSync(path.join(current, marker))) return current;\n }\n current = path.dirname(current);\n }\n return path.resolve(startDir);\n}\n\nexport const PROJECT_CONTEXT_FILE = \"project-context.md\";\nexport const MEMORIES_DIR = \"memories\";\n\nexport interface HaivePaths {\n root: string;\n haiveDir: string;\n projectContext: string;\n memoriesDir: string;\n personalDir: string;\n teamDir: string;\n moduleDir: string;\n modulesContextDir: string;\n}\n\nexport function resolveHaivePaths(projectRoot: string): HaivePaths {\n const haiveDir = path.join(projectRoot, HAIVE_DIR);\n const memoriesDir = path.join(haiveDir, MEMORIES_DIR);\n return {\n root: projectRoot,\n haiveDir,\n projectContext: path.join(haiveDir, PROJECT_CONTEXT_FILE),\n memoriesDir,\n personalDir: path.join(memoriesDir, \"personal\"),\n teamDir: path.join(memoriesDir, \"team\"),\n moduleDir: path.join(memoriesDir, \"module\"),\n modulesContextDir: path.join(haiveDir, \"modules\"),\n };\n}\n\nexport function memoryFilePath(\n paths: HaivePaths,\n scope: \"personal\" | \"team\" | \"module\",\n id: string,\n module?: string,\n): string {\n const base =\n scope === \"personal\"\n ? paths.personalDir\n : scope === \"team\"\n ? paths.teamDir\n : path.join(paths.moduleDir, module ?? \"_unscoped\");\n return path.join(base, `${id}.md`);\n}\n","import { readdir, readFile } from \"node:fs/promises\";\nimport path from \"node:path\";\nimport { parseMemory } from \"./parser.js\";\nimport type { Memory } from \"./types.js\";\n\nexport interface LoadedMemory {\n memory: Memory;\n filePath: string;\n}\n\nexport async function listMarkdownFilesRecursive(dir: string): Promise<string[]> {\n const out: string[] = [];\n let entries;\n try {\n entries = await readdir(dir, { withFileTypes: true });\n } catch {\n return out;\n }\n for (const entry of entries) {\n const full = path.join(dir, entry.name);\n if (entry.isDirectory()) {\n out.push(...(await listMarkdownFilesRecursive(full)));\n } else if (entry.isFile() && entry.name.endsWith(\".md\")) {\n out.push(full);\n }\n }\n return out;\n}\n\nexport async function loadMemory(filePath: string): Promise<LoadedMemory> {\n const raw = await readFile(filePath, \"utf8\");\n return { memory: parseMemory(raw), filePath };\n}\n\nexport async function loadMemoriesFromDir(dir: string): Promise<LoadedMemory[]> {\n const files = await listMarkdownFilesRecursive(dir);\n const out: LoadedMemory[] = [];\n for (const file of files) {\n try {\n out.push(await loadMemory(file));\n } catch {\n // Skip unparseable files in v0.1; future: surface a warning channel.\n }\n }\n return out;\n}\n","import type { Memory } from \"./types.js\";\n\nexport function tokenizeQuery(query: string): string[] {\n return query\n .toLowerCase()\n .split(/\\s+/)\n .map((t) => t.trim())\n .filter(Boolean);\n}\n\nexport function literalMatchesAllTokens(memory: Memory, tokens: string[]): boolean {\n if (tokens.length === 0) return true;\n const fm = memory.frontmatter;\n const idLower = fm.id.toLowerCase();\n const tagsLower = fm.tags.map((t) => t.toLowerCase());\n const bodyLower = memory.body.toLowerCase();\n const anchorPathTokens = collectAnchorPathTokens(fm.anchor.paths);\n const anchorSymbolsLower = fm.anchor.symbols.map((s) => s.toLowerCase());\n const moduleLower = fm.module?.toLowerCase();\n const domainLower = fm.domain?.toLowerCase();\n\n return tokens.every((rawTok) => {\n const tok = rawTok.toLowerCase();\n return (\n idLower.includes(tok) ||\n tagsLower.some((t) => t.includes(tok)) ||\n bodyLower.includes(tok) ||\n anchorPathTokens.some((p) => p.includes(tok)) ||\n anchorSymbolsLower.some((s) => s.includes(tok)) ||\n (moduleLower !== undefined && moduleLower.includes(tok)) ||\n (domainLower !== undefined && domainLower.includes(tok))\n );\n });\n}\n\nfunction collectAnchorPathTokens(paths: readonly string[]): string[] {\n const out = new Set<string>();\n for (const p of paths) {\n const lower = p.toLowerCase();\n out.add(lower);\n // basename without extension\n const base = lower.split(\"/\").pop() ?? lower;\n const noExt = base.replace(/\\.[a-z0-9]+$/, \"\");\n if (noExt) out.add(noExt);\n // each path segment (helps \"verifier\" match \"src/verifier.ts\")\n for (const segment of lower.split(\"/\")) {\n const seg = segment.replace(/\\.[a-z0-9]+$/, \"\");\n if (seg) out.add(seg);\n }\n }\n return [...out];\n}\n\n/**\n * OR-based fallback: returns true if the memory matches at least one token.\n * Used when all-tokens (AND) search returns 0 results.\n */\nexport function literalMatchesAnyToken(memory: Memory, tokens: string[]): boolean {\n if (tokens.length === 0) return false;\n const fm = memory.frontmatter;\n const idLower = fm.id.toLowerCase();\n const tagsLower = fm.tags.map((t) => t.toLowerCase());\n const bodyLower = memory.body.toLowerCase();\n const anchorPathTokens = collectAnchorPathTokens(fm.anchor.paths);\n const anchorSymbolsLower = fm.anchor.symbols.map((s) => s.toLowerCase());\n const moduleLower = fm.module?.toLowerCase();\n const domainLower = fm.domain?.toLowerCase();\n\n return tokens.some((rawTok) => {\n const tok = rawTok.toLowerCase();\n return (\n idLower.includes(tok) ||\n tagsLower.some((t) => t.includes(tok)) ||\n bodyLower.includes(tok) ||\n anchorPathTokens.some((p) => p.includes(tok)) ||\n anchorSymbolsLower.some((s) => s.includes(tok)) ||\n (moduleLower !== undefined && moduleLower.includes(tok)) ||\n (domainLower !== undefined && domainLower.includes(tok))\n );\n });\n}\n\nexport function pickSnippetNeedle(query: string): string {\n const tokens = tokenizeQuery(query);\n if (tokens.length === 0) return query.toLowerCase();\n return [...tokens].sort((a, b) => b.length - a.length)[0]!;\n}\n\nexport function extractSnippet(body: string, needle: string, radius = 40): string {\n const lower = body.toLowerCase();\n const idx = needle ? lower.indexOf(needle) : -1;\n if (idx < 0) {\n return body.slice(0, radius * 3).replace(/\\s+/g, \" \").trim();\n }\n const start = Math.max(0, idx - radius);\n const end = Math.min(body.length, idx + needle.length + radius);\n const snippet = body.slice(start, end).replace(/\\s+/g, \" \").trim();\n return (start > 0 ? \"…\" : \"\") + snippet + (end < body.length ? \"…\" : \"\");\n}\n","import { readFile, readdir, stat } from \"node:fs/promises\";\nimport { existsSync } from \"node:fs\";\nimport path from \"node:path\";\nimport type { Memory } from \"./types.js\";\n\nexport interface VerifyResult {\n stale: boolean;\n reason: string | null;\n checkedPaths: string[];\n checkedSymbols: string[];\n possibleRenames: string[];\n}\n\nexport interface VerifyOptions {\n /** Project root used to resolve relative anchor paths. */\n projectRoot: string;\n}\n\n/**\n * Verify that a memory's anchor still matches the current code.\n * - Every anchor.paths entry must exist on disk\n * - Every anchor.symbols entry must appear at least once across the anchor.paths\n * files (or any tracked file if no paths are recorded)\n *\n * Anchorless memories (no paths and no symbols) are always considered fresh —\n * staleness only applies to memories that opted into anchoring.\n */\nexport async function verifyAnchor(\n memory: Memory,\n options: VerifyOptions,\n): Promise<VerifyResult> {\n const anchor = memory.frontmatter.anchor;\n const checkedPaths = anchor.paths;\n const checkedSymbols = anchor.symbols;\n\n if (checkedPaths.length === 0 && checkedSymbols.length === 0) {\n return { stale: false, reason: null, checkedPaths, checkedSymbols, possibleRenames: [] };\n }\n\n const missingPaths: string[] = [];\n const existingAbsPaths: string[] = [];\n for (const rel of checkedPaths) {\n const abs = path.isAbsolute(rel) ? rel : path.join(options.projectRoot, rel);\n if (existsSync(abs)) {\n existingAbsPaths.push(abs);\n } else {\n missingPaths.push(rel);\n }\n }\n\n if (missingPaths.length > 0) {\n const possibleRenames = await findPossibleRenames(missingPaths, options.projectRoot);\n return {\n stale: true,\n reason: `anchor path(s) no longer exist: ${missingPaths.join(\", \")}`,\n checkedPaths,\n checkedSymbols,\n possibleRenames,\n };\n }\n\n if (checkedSymbols.length > 0) {\n if (existingAbsPaths.length === 0) {\n return {\n stale: true,\n reason: `cannot verify symbols (${checkedSymbols.join(\", \")}): no anchor paths recorded`,\n checkedPaths,\n checkedSymbols,\n possibleRenames: [],\n };\n }\n const missingSymbols: string[] = [];\n for (const sym of checkedSymbols) {\n let found = false;\n for (const file of existingAbsPaths) {\n try {\n const contents = await readFile(file, \"utf8\");\n if (contents.includes(sym)) {\n found = true;\n break;\n }\n } catch {\n // unreadable file; treat as not finding the symbol here\n }\n }\n if (!found) missingSymbols.push(sym);\n }\n if (missingSymbols.length > 0) {\n return {\n stale: true,\n reason: `anchor symbol(s) not found in any anchor path: ${missingSymbols.join(\", \")}`,\n checkedPaths,\n checkedSymbols,\n possibleRenames: [],\n };\n }\n }\n\n return { stale: false, reason: null, checkedPaths, checkedSymbols, possibleRenames: [] };\n}\n\nasync function findPossibleRenames(\n missingPaths: string[],\n projectRoot: string,\n): Promise<string[]> {\n const basenames = new Set(missingPaths.map((p) => path.basename(p)));\n const found: string[] = [];\n try {\n await walkDir(projectRoot, projectRoot, basenames, found, 0);\n } catch {\n // best-effort\n }\n return found;\n}\n\nasync function walkDir(\n dir: string,\n root: string,\n targets: Set<string>,\n found: string[],\n depth: number,\n): Promise<void> {\n if (depth > 6) return;\n let entries: string[];\n try {\n entries = await readdir(dir, { encoding: \"utf8\" });\n } catch {\n return;\n }\n for (const name of entries) {\n if (name.startsWith(\".\") || name === \"node_modules\") continue;\n const abs = path.join(dir, name);\n let isDir = false;\n try {\n isDir = (await stat(abs)).isDirectory();\n } catch {\n continue;\n }\n if (isDir) {\n await walkDir(abs, root, targets, found, depth + 1);\n } else if (targets.has(name)) {\n found.push(path.relative(root, abs));\n }\n }\n}\n","import { mkdir, readFile, writeFile } from \"node:fs/promises\";\nimport { existsSync } from \"node:fs\";\nimport path from \"node:path\";\nimport type { HaivePaths } from \"./paths.js\";\n\nexport interface MemoryUsage {\n read_count: number;\n last_read_at: string | null;\n rejected_count: number;\n last_rejected_at: string | null;\n rejection_reason: string | null;\n}\n\nexport interface UsageIndex {\n version: 1;\n updated_at: string;\n by_id: Record<string, MemoryUsage>;\n}\n\nexport const USAGE_FILE = \"usage.json\";\n\nexport function emptyUsage(): MemoryUsage {\n return {\n read_count: 0,\n last_read_at: null,\n rejected_count: 0,\n last_rejected_at: null,\n rejection_reason: null,\n };\n}\n\nexport function emptyUsageIndex(): UsageIndex {\n return {\n version: 1,\n updated_at: new Date().toISOString(),\n by_id: {},\n };\n}\n\nexport function usagePath(paths: HaivePaths): string {\n return path.join(paths.haiveDir, \".cache\", USAGE_FILE);\n}\n\nexport async function loadUsageIndex(paths: HaivePaths): Promise<UsageIndex> {\n const file = usagePath(paths);\n if (!existsSync(file)) return emptyUsageIndex();\n const raw = await readFile(file, \"utf8\");\n try {\n const parsed = JSON.parse(raw) as UsageIndex;\n if (parsed.version !== 1) return emptyUsageIndex();\n return parsed;\n } catch {\n return emptyUsageIndex();\n }\n}\n\nexport async function saveUsageIndex(paths: HaivePaths, index: UsageIndex): Promise<void> {\n const file = usagePath(paths);\n await mkdir(path.dirname(file), { recursive: true });\n index.updated_at = new Date().toISOString();\n await writeFile(file, JSON.stringify(index, null, 2), \"utf8\");\n}\n\nexport function getUsage(index: UsageIndex, id: string): MemoryUsage {\n return index.by_id[id] ?? emptyUsage();\n}\n\nexport function bumpRead(index: UsageIndex, ids: string[]): UsageIndex {\n if (ids.length === 0) return index;\n const now = new Date().toISOString();\n for (const id of ids) {\n const current = index.by_id[id] ?? emptyUsage();\n index.by_id[id] = {\n ...current,\n read_count: current.read_count + 1,\n last_read_at: now,\n };\n }\n return index;\n}\n\nexport function recordRejection(\n index: UsageIndex,\n id: string,\n reason: string | null,\n): UsageIndex {\n const current = index.by_id[id] ?? emptyUsage();\n const now = new Date().toISOString();\n index.by_id[id] = {\n ...current,\n rejected_count: current.rejected_count + 1,\n last_rejected_at: now,\n rejection_reason: reason,\n };\n return index;\n}\n\nexport const DECAY_DAYS = 90;\n\nexport function isDecaying(usage: MemoryUsage, createdAt: string): boolean {\n const threshold = Date.now() - DECAY_DAYS * 24 * 60 * 60 * 1000;\n const anchor = usage.last_read_at ?? createdAt;\n return new Date(anchor).getTime() < threshold;\n}\n\nexport async function trackReads(\n paths: HaivePaths,\n ids: string[],\n): Promise<UsageIndex> {\n if (ids.length === 0) {\n return await loadUsageIndex(paths);\n }\n const index = await loadUsageIndex(paths);\n bumpRead(index, ids);\n await saveUsageIndex(paths, index);\n return index;\n}\n","import type { MemoryFrontmatter } from \"./types.js\";\nimport type { MemoryUsage } from \"./usage.js\";\n\nexport type ConfidenceLevel =\n | \"unverified\"\n | \"low\"\n | \"trusted\"\n | \"authoritative\"\n | \"stale\";\n\nexport interface ConfidenceThresholds {\n trustedReads: number;\n authoritativeReads: number;\n}\n\nexport const DEFAULT_CONFIDENCE_THRESHOLDS: ConfidenceThresholds = {\n trustedReads: 3,\n authoritativeReads: 10,\n};\n\nexport function deriveConfidence(\n fm: MemoryFrontmatter,\n usage: MemoryUsage,\n thresholds: ConfidenceThresholds = DEFAULT_CONFIDENCE_THRESHOLDS,\n): ConfidenceLevel {\n if (fm.status === \"stale\" || fm.status === \"deprecated\" || fm.status === \"rejected\") return \"stale\";\n if (fm.status === \"validated\") {\n return usage.read_count >= thresholds.authoritativeReads\n ? \"authoritative\"\n : \"trusted\";\n }\n if (fm.status === \"proposed\") {\n return usage.read_count >= thresholds.trustedReads ? \"trusted\" : \"low\";\n }\n // draft\n return \"unverified\";\n}\n\nexport interface AutoPromoteRule {\n /** Minimum read_count to promote proposed → validated. */\n minReads: number;\n /** Maximum rejected_count tolerated (memories with more rejections never auto-promote). */\n maxRejections: number;\n}\n\nexport const DEFAULT_AUTO_PROMOTE_RULE: AutoPromoteRule = {\n minReads: 5,\n maxRejections: 0,\n};\n\nexport function isAutoPromoteEligible(\n fm: MemoryFrontmatter,\n usage: MemoryUsage,\n rule: AutoPromoteRule = DEFAULT_AUTO_PROMOTE_RULE,\n): boolean {\n if (fm.status !== \"proposed\") return false;\n if (usage.rejected_count > rule.maxRejections) return false;\n return usage.read_count >= rule.minReads;\n}\n","import path from \"node:path\";\nimport type { LoadedMemory } from \"./loader.js\";\n\nconst MODULE_PATTERNS = [\n /^packages\\/([^/]+)\\//,\n /^apps\\/([^/]+)\\//,\n /^modules\\/([^/]+)\\//,\n /^src\\/([^/]+)\\//,\n /^libs\\/([^/]+)\\//,\n /^services\\/([^/]+)\\//,\n /^internal\\/([^/]+)\\//,\n /^projects\\/([^/]+)\\//, // Nx layout\n /^cmd\\/([^/]+)\\//, // Go-style\n];\n\n/**\n * Best-effort inference: given a list of file paths, infer module names from\n * conventional layouts (packages/X/, apps/X/, modules/X/, src/X/).\n */\nexport function inferModulesFromPaths(filePaths: string[]): string[] {\n const out = new Set<string>();\n for (const p of filePaths) {\n const norm = normalize(p);\n for (const re of MODULE_PATTERNS) {\n const m = norm.match(re);\n if (m && m[1]) out.add(m[1]);\n }\n }\n return [...out].sort();\n}\n\n/**\n * Path overlap: returns true if `a` and `b` refer to the same path or one is a\n * parent of the other. Both inputs are treated as POSIX-style relative paths.\n */\nexport function pathsOverlap(a: string, b: string): boolean {\n const na = normalize(a);\n const nb = normalize(b);\n if (na === nb) return true;\n return na.startsWith(nb + \"/\") || nb.startsWith(na + \"/\");\n}\n\nexport function memoryMatchesAnchorPaths(\n memory: LoadedMemory[\"memory\"],\n inputPaths: string[],\n): boolean {\n const anchorPaths = memory.frontmatter.anchor.paths;\n if (anchorPaths.length === 0) return false;\n for (const ap of anchorPaths) {\n for (const ip of inputPaths) {\n if (pathsOverlap(ap, ip)) return true;\n }\n }\n return false;\n}\n\nfunction normalize(p: string): string {\n // Strip leading \"./\" and trailing \"/\", normalize separators.\n return p.replace(/\\\\/g, \"/\").replace(/^\\.\\//, \"\").replace(/\\/+$/, \"\");\n}\n\nexport function relPathFrom(root: string, abs: string): string {\n return path.relative(root, abs).replace(/\\\\/g, \"/\");\n}\n","/**\n * Token budgeting helpers. We use the standard heuristic of ~4 chars per token,\n * which is conservative for English/code/markdown. Callers that need exact\n * counts should plug in a real tokenizer; this module only ever over-estimates,\n * so the user's hard limits are respected.\n */\n\nexport const CHARS_PER_TOKEN = 4;\n\nexport function estimateTokens(text: string): number {\n return Math.ceil(text.length / CHARS_PER_TOKEN);\n}\n\nexport interface TruncateOptions {\n /** Maximum tokens allowed in the result (inclusive). */\n maxTokens: number;\n /** Marker inserted where content was dropped. */\n marker?: string;\n /** Where to keep characters from when truncating. Default: head. */\n mode?: \"head\" | \"tail\" | \"middle\";\n}\n\nexport interface TruncateResult {\n text: string;\n truncated: boolean;\n estimatedTokens: number;\n originalTokens: number;\n}\n\nconst DEFAULT_MARKER = \"\\n…[truncated]…\\n\";\n\nexport function truncateToTokens(\n input: string,\n options: TruncateOptions,\n): TruncateResult {\n const originalTokens = estimateTokens(input);\n const max = Math.max(0, options.maxTokens);\n if (originalTokens <= max) {\n return { text: input, truncated: false, estimatedTokens: originalTokens, originalTokens };\n }\n\n if (max === 0) {\n return { text: \"\", truncated: true, estimatedTokens: 0, originalTokens };\n }\n\n const marker = options.marker ?? DEFAULT_MARKER;\n const mode = options.mode ?? \"head\";\n const markerTokens = estimateTokens(marker);\n const budgetChars = Math.max(0, (max - markerTokens) * CHARS_PER_TOKEN);\n\n let result: string;\n if (budgetChars === 0) {\n result = \"\";\n } else if (mode === \"tail\") {\n result = marker + input.slice(input.length - budgetChars);\n } else if (mode === \"middle\") {\n const half = Math.floor(budgetChars / 2);\n result = input.slice(0, half) + marker + input.slice(input.length - half);\n } else {\n result = input.slice(0, budgetChars) + marker;\n }\n\n return {\n text: result,\n truncated: true,\n estimatedTokens: estimateTokens(result),\n originalTokens,\n };\n}\n\n/**\n * Allocate a global token budget across N parts with relative weights, then\n * truncate each part to its share. Returns parts in input order, paired with\n * truncate metadata.\n */\nexport interface BudgetPart {\n key: string;\n text: string;\n weight: number;\n mode?: TruncateOptions[\"mode\"];\n}\n\nexport interface BudgetSlice {\n key: string;\n text: string;\n truncated: boolean;\n estimatedTokens: number;\n originalTokens: number;\n allocatedTokens: number;\n}\n\nexport function allocateBudget(\n parts: BudgetPart[],\n maxTokens: number,\n): BudgetSlice[] {\n if (parts.length === 0) return [];\n const totalWeight = parts.reduce((s, p) => s + Math.max(0, p.weight), 0);\n if (totalWeight === 0) {\n return parts.map((p) => ({\n key: p.key,\n text: \"\",\n truncated: estimateTokens(p.text) > 0,\n estimatedTokens: 0,\n originalTokens: estimateTokens(p.text),\n allocatedTokens: 0,\n }));\n }\n\n // First pass: allocate by weight, but if a part's content fits in less than\n // its share, redistribute the surplus to others proportionally.\n const allocations = new Map<string, number>();\n let remaining = maxTokens;\n let remainingWeight = totalWeight;\n\n // Sort parts by share fit ascending so small ones consume their share first.\n const sortedByFit = [...parts]\n .map((p) => ({\n key: p.key,\n tokens: estimateTokens(p.text),\n share: (p.weight / totalWeight) * maxTokens,\n part: p,\n }))\n .sort((a, b) => a.tokens - b.tokens);\n\n for (const item of sortedByFit) {\n const myShare = remainingWeight > 0\n ? (item.part.weight / remainingWeight) * remaining\n : 0;\n const grant = Math.min(item.tokens, Math.floor(myShare));\n allocations.set(item.key, grant);\n remaining -= grant;\n remainingWeight -= item.part.weight;\n }\n\n return parts.map((p) => {\n const allocated = allocations.get(p.key) ?? 0;\n const truncated = truncateToTokens(p.text, {\n maxTokens: allocated,\n mode: p.mode ?? \"head\",\n });\n return {\n key: p.key,\n text: truncated.text,\n truncated: truncated.truncated,\n estimatedTokens: truncated.estimatedTokens,\n originalTokens: truncated.originalTokens,\n allocatedTokens: allocated,\n };\n });\n}\n","import { mkdir, readFile, readdir, writeFile } from \"node:fs/promises\";\nimport { existsSync } from \"node:fs\";\nimport path from \"node:path\";\nimport type { HaivePaths } from \"./paths.js\";\n\nexport const CODE_MAP_FILE = \"code-map.json\";\n\nexport type CodeExportKind =\n | \"function\"\n | \"class\"\n | \"interface\"\n | \"type\"\n | \"const\"\n | \"enum\"\n | \"default\";\n\nexport interface CodeExport {\n name: string;\n kind: CodeExportKind;\n description?: string;\n line: number;\n}\n\nexport interface CodeFileEntry {\n summary?: string;\n exports: CodeExport[];\n loc: number;\n}\n\nexport interface CodeMap {\n version: 1;\n generated_at: string;\n root: string;\n files: Record<string, CodeFileEntry>;\n}\n\nexport interface BuildCodeMapOptions {\n includeExtensions?: string[];\n excludeDirs?: string[];\n}\n\nconst DEFAULT_INCLUDE = [\n \".ts\", \".tsx\", \".js\", \".jsx\", \".mjs\", \".cjs\",\n \".java\", \".kt\",\n \".py\",\n \".go\",\n \".rb\",\n \".rs\",\n \".cs\",\n \".php\",\n];\nconst DEFAULT_EXCLUDE = [\n \"node_modules\",\n \"dist\",\n \"build\",\n \"out\",\n \".git\",\n \".next\",\n \".turbo\",\n \".vitest-cache\",\n \"coverage\",\n \"test\",\n \"tests\",\n \"__tests__\",\n \"__mocks__\",\n \"target\", // Maven/Gradle build output\n \".gradle\",\n \"__pycache__\",\n \".pytest_cache\",\n \"vendor\", // Go / PHP\n];\n\nconst TEST_FILE_RE = /\\.(test|spec)\\.[a-z]+$/i;\n\nexport function codeMapPath(paths: HaivePaths): string {\n return path.join(paths.haiveDir, CODE_MAP_FILE);\n}\n\nexport async function loadCodeMap(paths: HaivePaths): Promise<CodeMap | null> {\n const file = codeMapPath(paths);\n if (!existsSync(file)) return null;\n return JSON.parse(await readFile(file, \"utf8\")) as CodeMap;\n}\n\nexport async function saveCodeMap(paths: HaivePaths, map: CodeMap): Promise<void> {\n const file = codeMapPath(paths);\n await mkdir(path.dirname(file), { recursive: true });\n await writeFile(file, JSON.stringify(map, null, 2), \"utf8\");\n}\n\nexport async function buildCodeMap(\n root: string,\n options: BuildCodeMapOptions = {},\n): Promise<CodeMap> {\n const include = new Set(options.includeExtensions ?? DEFAULT_INCLUDE);\n const exclude = new Set(options.excludeDirs ?? DEFAULT_EXCLUDE);\n const files: Record<string, CodeFileEntry> = {};\n\n for await (const abs of walkSourceFiles(root, include, exclude)) {\n const rel = path.relative(root, abs).replace(/\\\\/g, \"/\");\n if (rel.startsWith(\".ai/\")) continue;\n const content = await readFile(abs, \"utf8\");\n const ext = path.extname(abs).toLowerCase();\n const entry = parseFile(content, ext);\n if (entry.exports.length > 0) files[rel] = entry;\n }\n\n return {\n version: 1,\n generated_at: new Date().toISOString(),\n root,\n files,\n };\n}\n\nasync function* walkSourceFiles(\n dir: string,\n include: Set<string>,\n exclude: Set<string>,\n): AsyncGenerator<string> {\n let entries;\n try {\n entries = await readdir(dir, { withFileTypes: true });\n } catch {\n return;\n }\n for (const entry of entries) {\n if (entry.name.startsWith(\".\") && entry.name !== \".github\") {\n // Skip hidden dirs except .github (workflows can be useful)\n if (entry.isDirectory()) continue;\n }\n if (exclude.has(entry.name)) continue;\n const full = path.join(dir, entry.name);\n if (entry.isDirectory()) {\n yield* walkSourceFiles(full, include, exclude);\n } else if (entry.isFile()) {\n const ext = path.extname(entry.name).toLowerCase();\n if (include.has(ext) && !TEST_FILE_RE.test(entry.name)) yield full;\n }\n }\n}\n\nconst EXPORT_RE =\n /^export\\s+(?:default\\s+)?(async\\s+)?(function|class|interface|type|const|let|var|enum)\\s+(\\*?)\\s*([A-Za-z_$][\\w$]*)/gm;\n\nconst NAMED_REEXPORT_RE = /^export\\s*\\{([^}]+)\\}/gm;\n\nconst FILE_HEADER_COMMENT_RE = /^\\/\\*\\*([\\s\\S]*?)\\*\\//;\n\n// Java / Kotlin: public/protected class, interface, enum, record, @interface, fun, @RestController etc.\nconst JAVA_DECL_RE =\n /^(?:[ \\t]*)(?:@\\w+\\s+)*(?:public|protected|private|internal)?\\s*(?:static\\s+|final\\s+|abstract\\s+|open\\s+|data\\s+|sealed\\s+)*(?:(class|interface|enum|record|@interface|object)\\s+([A-Z][A-Za-z0-9_$]*)|(fun|def|func|function)\\s+([a-z_][A-Za-z0-9_$]*))/gm;\n\n// Python: def / class at module level (not indented)\nconst PYTHON_DECL_RE = /^(def|class)\\s+([A-Za-z_][A-Za-z0-9_]*)/gm;\n\n// Go: func declarations\nconst GO_DECL_RE = /^func\\s+(?:\\(\\w+\\s+\\*?[A-Za-z_][\\w]*\\)\\s+)?([A-Za-z_][A-Za-z0-9_]*)/gm;\n\n// Rust: pub fn / pub struct / pub enum / pub trait\nconst RUST_DECL_RE =\n /^pub(?:\\([^)]*\\))?\\s+(fn|struct|enum|trait|type|const|impl|mod)\\s+([A-Za-z_][A-Za-z0-9_]*)/gm;\n\nfunction parseFile(source: string, ext: string): CodeFileEntry {\n if (ext === \".java\" || ext === \".kt\") return parseJvmFile(source);\n if (ext === \".py\") return parsePythonFile(source);\n if (ext === \".go\") return parseGoFile(source);\n if (ext === \".rs\") return parseRustFile(source);\n return parseJsFile(source);\n}\n\nfunction parseJsFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n\n let m: RegExpExecArray | null;\n EXPORT_RE.lastIndex = 0;\n while ((m = EXPORT_RE.exec(source))) {\n const kindRaw = m[2] ?? \"\";\n const name = m[4] ?? \"\";\n if (!name) continue;\n const kind: CodeExportKind =\n kindRaw === \"function\" ? \"function\" :\n kindRaw === \"class\" ? \"class\" :\n kindRaw === \"interface\" ? \"interface\" :\n kindRaw === \"type\" ? \"type\" :\n kindRaw === \"enum\" ? \"enum\" : \"const\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n\n NAMED_REEXPORT_RE.lastIndex = 0;\n while ((m = NAMED_REEXPORT_RE.exec(source))) {\n const inside = m[1] ?? \"\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n for (const part of inside.split(\",\")) {\n const cleaned = part.trim().split(/\\s+as\\s+/).pop()?.trim() ?? \"\";\n if (!cleaned || cleaned.startsWith(\"type \")) continue;\n if (exports.some((e) => e.name === cleaned)) continue;\n exports.push({ name: cleaned, kind: \"const\", line: lineIdx + 1 });\n }\n }\n\n const summary = extractFileSummary(source);\n return { ...(summary ? { summary } : {}), exports, loc: source.split(\"\\n\").length };\n}\n\nfunction parseJvmFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n JAVA_DECL_RE.lastIndex = 0;\n while ((m = JAVA_DECL_RE.exec(source))) {\n const kindRaw = m[1] ?? m[3] ?? \"\";\n const name = m[2] ?? m[4] ?? \"\";\n if (!name) continue;\n const kind: CodeExportKind =\n kindRaw === \"class\" || kindRaw === \"record\" || kindRaw === \"object\" ? \"class\" :\n kindRaw === \"interface\" || kindRaw === \"@interface\" ? \"interface\" :\n kindRaw === \"enum\" ? \"enum\" :\n kindRaw === \"fun\" || kindRaw === \"def\" || kindRaw === \"func\" || kindRaw === \"function\" ? \"function\" :\n \"const\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n const summary = extractJavaSummary(source);\n return { ...(summary ? { summary } : {}), exports, loc: lines.length };\n}\n\nfunction parsePythonFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n PYTHON_DECL_RE.lastIndex = 0;\n while ((m = PYTHON_DECL_RE.exec(source))) {\n const keyword = m[1] ?? \"\";\n const name = m[2] ?? \"\";\n if (!name || name.startsWith(\"_\")) continue;\n const kind: CodeExportKind = keyword === \"class\" ? \"class\" : \"function\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractPythonDocstring(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n const summary = extractPythonModuleDocstring(source);\n return { ...(summary ? { summary } : {}), exports, loc: lines.length };\n}\n\nfunction parseGoFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n GO_DECL_RE.lastIndex = 0;\n while ((m = GO_DECL_RE.exec(source))) {\n const name = m[1] ?? \"\";\n if (!name || !/^[A-Z]/.test(name)) continue; // Only exported (uppercase) in Go\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind: \"function\", ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n return { exports, loc: lines.length };\n}\n\nfunction parseRustFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n RUST_DECL_RE.lastIndex = 0;\n while ((m = RUST_DECL_RE.exec(source))) {\n const kindRaw = m[1] ?? \"\";\n const name = m[2] ?? \"\";\n if (!name) continue;\n const kind: CodeExportKind =\n kindRaw === \"struct\" || kindRaw === \"impl\" ? \"class\" :\n kindRaw === \"enum\" ? \"enum\" :\n kindRaw === \"trait\" ? \"interface\" :\n kindRaw === \"fn\" ? \"function\" :\n kindRaw === \"type\" ? \"type\" : \"const\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n return { exports, loc: lines.length };\n}\n\nfunction extractJavaSummary(source: string): string | undefined {\n // Java/Kotlin: file-level Javadoc before first class/interface\n const m = source.match(/^\\/\\*\\*([\\s\\S]*?)\\*\\//);\n if (!m) return undefined;\n const block = (m[1] ?? \"\")\n .split(\"\\n\")\n .map((l) => l.replace(/^\\s*\\*\\s?/, \"\").trim())\n .filter((l) => l && !l.startsWith(\"@\"))\n .join(\" \");\n return block ? firstSentence(block) : undefined;\n}\n\nfunction extractPythonDocstring(lines: string[], defLine: number): string | undefined {\n const next = lines[defLine + 1] ?? \"\";\n const stripped = next.trim();\n if (stripped.startsWith('\"\"\"') || stripped.startsWith(\"'''\")) {\n const inner = stripped.replace(/^[\"']{3}/, \"\").replace(/[\"']{3}.*$/, \"\").trim();\n return inner || undefined;\n }\n return undefined;\n}\n\nfunction extractPythonModuleDocstring(source: string): string | undefined {\n const m = source.match(/^[\"']{3}([\\s\\S]*?)[\"']{3}/);\n if (!m) return undefined;\n return firstSentence((m[1] ?? \"\").trim());\n}\n\nfunction computeLineOffsets(source: string): number[] {\n const out: number[] = [0];\n for (let i = 0; i < source.length; i++) {\n if (source[i] === \"\\n\") out.push(i + 1);\n }\n return out;\n}\n\nfunction byteToLine(byte: number, offsets: number[]): number {\n let lo = 0;\n let hi = offsets.length - 1;\n while (lo < hi) {\n const mid = (lo + hi + 1) >> 1;\n const off = offsets[mid] ?? 0;\n if (off <= byte) lo = mid;\n else hi = mid - 1;\n }\n return lo;\n}\n\nfunction extractJSDocAbove(lines: string[], exportLine: number): string | undefined {\n let i = exportLine - 1;\n // Skip blank lines between JSDoc and export\n while (i >= 0 && (lines[i] ?? \"\").trim() === \"\") i--;\n if (i < 0) return undefined;\n const line = (lines[i] ?? \"\").trim();\n\n if (line.startsWith(\"//\")) {\n return line.replace(/^\\/\\/\\s*/, \"\").trim() || undefined;\n }\n\n // Single-line JSDoc: /** Adds two numbers. */\n const singleLine = line.match(/^\\/\\*\\*\\s*(.*?)\\s*\\*\\/\\s*$/);\n if (singleLine && singleLine[1]) {\n return firstSentence(singleLine[1]);\n }\n\n if (line.endsWith(\"*/\")) {\n // Walk up until /**\n const collected: string[] = [];\n // First piece: content of the line before */\n const firstPiece = line.replace(/\\*\\/\\s*$/, \"\").replace(/^\\*\\s?/, \"\").trim();\n if (firstPiece) collected.unshift(firstPiece);\n let j = i - 1;\n while (j >= 0) {\n const l = (lines[j] ?? \"\").trim();\n if (l.startsWith(\"/**\")) {\n const inner = l.replace(/^\\/\\*\\*/, \"\").trim();\n if (inner) collected.unshift(inner);\n break;\n }\n collected.unshift(l.replace(/^\\*\\s?/, \"\").trim());\n j--;\n }\n const joined = collected.join(\" \").trim();\n if (!joined) return undefined;\n return firstSentence(joined);\n }\n return undefined;\n}\n\nfunction firstSentence(text: string): string | undefined {\n const trimmed = text.trim();\n if (!trimmed) return undefined;\n return trimmed.split(/(?<=\\.)\\s+/)[0]?.trim();\n}\n\nfunction extractFileSummary(source: string): string | undefined {\n const m = source.match(FILE_HEADER_COMMENT_RE);\n if (!m) return undefined;\n const block = (m[1] ?? \"\")\n .split(\"\\n\")\n .map((l) => l.replace(/^\\s*\\*\\s?/, \"\").trim())\n .filter(Boolean)\n .join(\" \");\n if (!block) return undefined;\n const sentence = block.split(/(?<=\\.)\\s+/)[0]?.trim();\n return sentence;\n}\n\nexport interface CodeMapQueryOptions {\n file?: string;\n symbol?: string;\n}\n\nexport function queryCodeMap(map: CodeMap, options: CodeMapQueryOptions): {\n files: Array<{ path: string; entry: CodeFileEntry }>;\n} {\n const files: Array<{ path: string; entry: CodeFileEntry }> = [];\n for (const [filePath, entry] of Object.entries(map.files)) {\n if (options.file) {\n if (!filePath.includes(options.file)) continue;\n }\n if (options.symbol) {\n const sym = options.symbol.toLowerCase();\n if (!entry.exports.some((e) => e.name.toLowerCase().includes(sym))) continue;\n }\n files.push({ path: filePath, entry });\n }\n return { files };\n}\n"],"mappings":"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","names":["path","path","readFile","readdir","existsSync","path","readFile","existsSync","path","path","mkdir","readFile","readdir","writeFile","existsSync","path"]}
|
|
1
|
+
{"version":3,"sources":["../src/schema.ts","../src/parser.ts","../src/paths.ts","../src/loader.ts","../src/search.ts","../src/verifier.ts","../src/usage.ts","../src/confidence.ts","../src/relevance.ts","../src/token-budget.ts","../src/code-map.ts"],"sourcesContent":["import { z } from \"zod\";\n\nexport const MemoryScopeSchema = z.enum([\"personal\", \"team\", \"module\"]);\n\nexport const MemoryStatusSchema = z.enum([\n \"draft\",\n \"proposed\",\n \"validated\",\n \"deprecated\",\n \"stale\",\n \"rejected\",\n]);\n\nexport const MemoryTypeSchema = z.enum([\n \"convention\",\n \"decision\",\n \"gotcha\",\n \"architecture\",\n \"glossary\",\n \"attempt\", // failed approach — \"tried X, failed because Y, use Z instead\"\n \"session_recap\", // end-of-session summary: goal / accomplished / discoveries / next steps\n]);\n\nexport const AnchorSchema = z.object({\n commit: z.string().optional(),\n paths: z.array(z.string()).default([]),\n symbols: z.array(z.string()).default([]),\n});\n\nconst IsoDateString = z\n .union([z.string(), z.date()])\n .transform((v) => (v instanceof Date ? v.toISOString() : v))\n .pipe(z.string().datetime());\n\nexport const MemoryFrontmatterSchema = z\n .object({\n id: z.string().min(1),\n scope: MemoryScopeSchema.default(\"personal\"),\n module: z.string().optional(),\n type: MemoryTypeSchema,\n status: MemoryStatusSchema.default(\"draft\"),\n anchor: AnchorSchema.default({ paths: [], symbols: [] }),\n tags: z.array(z.string()).default([]),\n domain: z.string().optional(),\n author: z.string().optional(),\n created_at: IsoDateString,\n expires_when: z.string().nullable().default(null),\n verified_at: z.string().nullable().default(null),\n stale_reason: z.string().nullable().default(null),\n related_ids: z.array(z.string()).default([]),\n last_read_at: z.string().nullable().default(null),\n topic: z.string().optional(), // stable key for upsert — same topic in same scope → update instead of create\n revision_count: z.number().int().min(0).default(0), // incremented each time a topic upsert occurs\n })\n .refine(\n (data) => data.scope !== \"module\" || !!data.module,\n { message: \"module name is required when scope is 'module'\", path: [\"module\"] },\n );\n","import matter from \"gray-matter\";\nimport { MemoryFrontmatterSchema } from \"./schema.js\";\nimport type { Memory, MemoryFrontmatter } from \"./types.js\";\n\nconst PRIVATE_BLOCK_RE = /<private>[\\s\\S]*?<\\/private>/g;\n\nexport function stripPrivate(body: string): string {\n return body.replace(PRIVATE_BLOCK_RE, \"\").trimEnd();\n}\n\nexport function parseMemory(raw: string): Memory {\n const parsed = matter(raw);\n const frontmatter = MemoryFrontmatterSchema.parse(parsed.data);\n return {\n frontmatter,\n body: stripPrivate(parsed.content.trim()),\n };\n}\n\nfunction stripUndefined<T>(value: T): T {\n if (Array.isArray(value)) {\n return value.map((v) => stripUndefined(v)) as unknown as T;\n }\n if (value && typeof value === \"object\") {\n const out: Record<string, unknown> = {};\n for (const [k, v] of Object.entries(value as Record<string, unknown>)) {\n if (v === undefined) continue;\n out[k] = stripUndefined(v);\n }\n return out as T;\n }\n return value;\n}\n\nexport function serializeMemory(memory: Memory): string {\n const clean = stripUndefined(memory.frontmatter) as Record<string, unknown>;\n return matter.stringify(memory.body, clean);\n}\n\nexport function newMemoryId(type: string, slug: string, date = new Date()): string {\n const isoDate = date.toISOString().slice(0, 10);\n const safeSlug = slug\n .toLowerCase()\n .replace(/[^a-z0-9]+/g, \"-\")\n .replace(/^-|-$/g, \"\")\n .slice(0, 60);\n return `${isoDate}-${type}-${safeSlug}`;\n}\n\nexport function buildFrontmatter(input: {\n type: MemoryFrontmatter[\"type\"];\n slug: string;\n scope?: MemoryFrontmatter[\"scope\"];\n module?: string;\n tags?: string[];\n domain?: string;\n author?: string;\n paths?: string[];\n symbols?: string[];\n commit?: string;\n topic?: string;\n status?: MemoryFrontmatter[\"status\"];\n}): MemoryFrontmatter {\n const now = new Date();\n const id = newMemoryId(input.type, input.slug, now);\n return MemoryFrontmatterSchema.parse({\n id,\n scope: input.scope ?? \"personal\",\n module: input.module,\n type: input.type,\n status: input.status ?? \"draft\",\n anchor: {\n commit: input.commit,\n paths: input.paths ?? [],\n symbols: input.symbols ?? [],\n },\n tags: input.tags ?? [],\n domain: input.domain,\n author: input.author,\n created_at: now.toISOString(),\n expires_when: null,\n topic: input.topic,\n revision_count: 0,\n });\n}\n","import { existsSync } from \"node:fs\";\nimport path from \"node:path\";\n\nexport const HAIVE_DIR = \".ai\";\n\nconst ROOT_MARKERS = [\".ai\", \".git\", \"package.json\"];\n\nexport function findProjectRoot(startDir: string = process.cwd()): string {\n let current = path.resolve(startDir);\n const fsRoot = path.parse(current).root;\n while (current !== fsRoot) {\n for (const marker of ROOT_MARKERS) {\n if (existsSync(path.join(current, marker))) return current;\n }\n current = path.dirname(current);\n }\n return path.resolve(startDir);\n}\n\nexport const PROJECT_CONTEXT_FILE = \"project-context.md\";\nexport const MEMORIES_DIR = \"memories\";\n\nexport interface HaivePaths {\n root: string;\n haiveDir: string;\n projectContext: string;\n memoriesDir: string;\n personalDir: string;\n teamDir: string;\n moduleDir: string;\n modulesContextDir: string;\n}\n\nexport function resolveHaivePaths(projectRoot: string): HaivePaths {\n const haiveDir = path.join(projectRoot, HAIVE_DIR);\n const memoriesDir = path.join(haiveDir, MEMORIES_DIR);\n return {\n root: projectRoot,\n haiveDir,\n projectContext: path.join(haiveDir, PROJECT_CONTEXT_FILE),\n memoriesDir,\n personalDir: path.join(memoriesDir, \"personal\"),\n teamDir: path.join(memoriesDir, \"team\"),\n moduleDir: path.join(memoriesDir, \"module\"),\n modulesContextDir: path.join(haiveDir, \"modules\"),\n };\n}\n\nexport function memoryFilePath(\n paths: HaivePaths,\n scope: \"personal\" | \"team\" | \"module\",\n id: string,\n module?: string,\n): string {\n const base =\n scope === \"personal\"\n ? paths.personalDir\n : scope === \"team\"\n ? paths.teamDir\n : path.join(paths.moduleDir, module ?? \"_unscoped\");\n return path.join(base, `${id}.md`);\n}\n","import { readdir, readFile } from \"node:fs/promises\";\nimport path from \"node:path\";\nimport { parseMemory } from \"./parser.js\";\nimport type { Memory } from \"./types.js\";\n\nexport interface LoadedMemory {\n memory: Memory;\n filePath: string;\n}\n\nexport async function listMarkdownFilesRecursive(dir: string): Promise<string[]> {\n const out: string[] = [];\n let entries;\n try {\n entries = await readdir(dir, { withFileTypes: true });\n } catch {\n return out;\n }\n for (const entry of entries) {\n const full = path.join(dir, entry.name);\n if (entry.isDirectory()) {\n out.push(...(await listMarkdownFilesRecursive(full)));\n } else if (entry.isFile() && entry.name.endsWith(\".md\")) {\n out.push(full);\n }\n }\n return out;\n}\n\nexport async function loadMemory(filePath: string): Promise<LoadedMemory> {\n const raw = await readFile(filePath, \"utf8\");\n return { memory: parseMemory(raw), filePath };\n}\n\nexport async function loadMemoriesFromDir(dir: string): Promise<LoadedMemory[]> {\n const files = await listMarkdownFilesRecursive(dir);\n const out: LoadedMemory[] = [];\n for (const file of files) {\n try {\n out.push(await loadMemory(file));\n } catch {\n // Skip unparseable files in v0.1; future: surface a warning channel.\n }\n }\n return out;\n}\n","import type { Memory } from \"./types.js\";\n\nexport function tokenizeQuery(query: string): string[] {\n return query\n .toLowerCase()\n .split(/\\s+/)\n .map((t) => t.trim())\n .filter(Boolean);\n}\n\nexport function literalMatchesAllTokens(memory: Memory, tokens: string[]): boolean {\n if (tokens.length === 0) return true;\n const fm = memory.frontmatter;\n const idLower = fm.id.toLowerCase();\n const tagsLower = fm.tags.map((t) => t.toLowerCase());\n const bodyLower = memory.body.toLowerCase();\n const anchorPathTokens = collectAnchorPathTokens(fm.anchor.paths);\n const anchorSymbolsLower = fm.anchor.symbols.map((s) => s.toLowerCase());\n const moduleLower = fm.module?.toLowerCase();\n const domainLower = fm.domain?.toLowerCase();\n\n return tokens.every((rawTok) => {\n const tok = rawTok.toLowerCase();\n return (\n idLower.includes(tok) ||\n tagsLower.some((t) => t.includes(tok)) ||\n bodyLower.includes(tok) ||\n anchorPathTokens.some((p) => p.includes(tok)) ||\n anchorSymbolsLower.some((s) => s.includes(tok)) ||\n (moduleLower !== undefined && moduleLower.includes(tok)) ||\n (domainLower !== undefined && domainLower.includes(tok))\n );\n });\n}\n\nfunction collectAnchorPathTokens(paths: readonly string[]): string[] {\n const out = new Set<string>();\n for (const p of paths) {\n const lower = p.toLowerCase();\n out.add(lower);\n // basename without extension\n const base = lower.split(\"/\").pop() ?? lower;\n const noExt = base.replace(/\\.[a-z0-9]+$/, \"\");\n if (noExt) out.add(noExt);\n // each path segment (helps \"verifier\" match \"src/verifier.ts\")\n for (const segment of lower.split(\"/\")) {\n const seg = segment.replace(/\\.[a-z0-9]+$/, \"\");\n if (seg) out.add(seg);\n }\n }\n return [...out];\n}\n\n/**\n * OR-based fallback: returns true if the memory matches at least one token.\n * Used when all-tokens (AND) search returns 0 results.\n */\nexport function literalMatchesAnyToken(memory: Memory, tokens: string[]): boolean {\n if (tokens.length === 0) return false;\n const fm = memory.frontmatter;\n const idLower = fm.id.toLowerCase();\n const tagsLower = fm.tags.map((t) => t.toLowerCase());\n const bodyLower = memory.body.toLowerCase();\n const anchorPathTokens = collectAnchorPathTokens(fm.anchor.paths);\n const anchorSymbolsLower = fm.anchor.symbols.map((s) => s.toLowerCase());\n const moduleLower = fm.module?.toLowerCase();\n const domainLower = fm.domain?.toLowerCase();\n\n return tokens.some((rawTok) => {\n const tok = rawTok.toLowerCase();\n return (\n idLower.includes(tok) ||\n tagsLower.some((t) => t.includes(tok)) ||\n bodyLower.includes(tok) ||\n anchorPathTokens.some((p) => p.includes(tok)) ||\n anchorSymbolsLower.some((s) => s.includes(tok)) ||\n (moduleLower !== undefined && moduleLower.includes(tok)) ||\n (domainLower !== undefined && domainLower.includes(tok))\n );\n });\n}\n\nexport function pickSnippetNeedle(query: string): string {\n const tokens = tokenizeQuery(query);\n if (tokens.length === 0) return query.toLowerCase();\n return [...tokens].sort((a, b) => b.length - a.length)[0]!;\n}\n\nexport function extractSnippet(body: string, needle: string, radius = 40): string {\n const lower = body.toLowerCase();\n const idx = needle ? lower.indexOf(needle) : -1;\n if (idx < 0) {\n return body.slice(0, radius * 3).replace(/\\s+/g, \" \").trim();\n }\n const start = Math.max(0, idx - radius);\n const end = Math.min(body.length, idx + needle.length + radius);\n const snippet = body.slice(start, end).replace(/\\s+/g, \" \").trim();\n return (start > 0 ? \"…\" : \"\") + snippet + (end < body.length ? \"…\" : \"\");\n}\n","import { readFile, readdir, stat } from \"node:fs/promises\";\nimport { existsSync } from \"node:fs\";\nimport path from \"node:path\";\nimport type { Memory } from \"./types.js\";\n\nexport interface VerifyResult {\n stale: boolean;\n reason: string | null;\n checkedPaths: string[];\n checkedSymbols: string[];\n possibleRenames: string[];\n}\n\nexport interface VerifyOptions {\n /** Project root used to resolve relative anchor paths. */\n projectRoot: string;\n}\n\n/**\n * Verify that a memory's anchor still matches the current code.\n * - Every anchor.paths entry must exist on disk\n * - Every anchor.symbols entry must appear at least once across the anchor.paths\n * files (or any tracked file if no paths are recorded)\n *\n * Anchorless memories (no paths and no symbols) are always considered fresh —\n * staleness only applies to memories that opted into anchoring.\n */\nexport async function verifyAnchor(\n memory: Memory,\n options: VerifyOptions,\n): Promise<VerifyResult> {\n const anchor = memory.frontmatter.anchor;\n const checkedPaths = anchor.paths;\n const checkedSymbols = anchor.symbols;\n\n if (checkedPaths.length === 0 && checkedSymbols.length === 0) {\n return { stale: false, reason: null, checkedPaths, checkedSymbols, possibleRenames: [] };\n }\n\n const missingPaths: string[] = [];\n const existingAbsPaths: string[] = [];\n for (const rel of checkedPaths) {\n const abs = path.isAbsolute(rel) ? rel : path.join(options.projectRoot, rel);\n if (existsSync(abs)) {\n existingAbsPaths.push(abs);\n } else {\n missingPaths.push(rel);\n }\n }\n\n if (missingPaths.length > 0) {\n const possibleRenames = await findPossibleRenames(missingPaths, options.projectRoot);\n return {\n stale: true,\n reason: `anchor path(s) no longer exist: ${missingPaths.join(\", \")}`,\n checkedPaths,\n checkedSymbols,\n possibleRenames,\n };\n }\n\n if (checkedSymbols.length > 0) {\n if (existingAbsPaths.length === 0) {\n return {\n stale: true,\n reason: `cannot verify symbols (${checkedSymbols.join(\", \")}): no anchor paths recorded`,\n checkedPaths,\n checkedSymbols,\n possibleRenames: [],\n };\n }\n const missingSymbols: string[] = [];\n for (const sym of checkedSymbols) {\n let found = false;\n for (const file of existingAbsPaths) {\n try {\n const contents = await readFile(file, \"utf8\");\n if (contents.includes(sym)) {\n found = true;\n break;\n }\n } catch {\n // unreadable file; treat as not finding the symbol here\n }\n }\n if (!found) missingSymbols.push(sym);\n }\n if (missingSymbols.length > 0) {\n return {\n stale: true,\n reason: `anchor symbol(s) not found in any anchor path: ${missingSymbols.join(\", \")}`,\n checkedPaths,\n checkedSymbols,\n possibleRenames: [],\n };\n }\n }\n\n return { stale: false, reason: null, checkedPaths, checkedSymbols, possibleRenames: [] };\n}\n\nasync function findPossibleRenames(\n missingPaths: string[],\n projectRoot: string,\n): Promise<string[]> {\n const basenames = new Set(missingPaths.map((p) => path.basename(p)));\n const found: string[] = [];\n try {\n await walkDir(projectRoot, projectRoot, basenames, found, 0);\n } catch {\n // best-effort\n }\n return found;\n}\n\nasync function walkDir(\n dir: string,\n root: string,\n targets: Set<string>,\n found: string[],\n depth: number,\n): Promise<void> {\n if (depth > 6) return;\n let entries: string[];\n try {\n entries = await readdir(dir, { encoding: \"utf8\" });\n } catch {\n return;\n }\n for (const name of entries) {\n if (name.startsWith(\".\") || name === \"node_modules\") continue;\n const abs = path.join(dir, name);\n let isDir = false;\n try {\n isDir = (await stat(abs)).isDirectory();\n } catch {\n continue;\n }\n if (isDir) {\n await walkDir(abs, root, targets, found, depth + 1);\n } else if (targets.has(name)) {\n found.push(path.relative(root, abs));\n }\n }\n}\n","import { mkdir, readFile, writeFile } from \"node:fs/promises\";\nimport { existsSync } from \"node:fs\";\nimport path from \"node:path\";\nimport type { HaivePaths } from \"./paths.js\";\n\nexport interface MemoryUsage {\n read_count: number;\n last_read_at: string | null;\n rejected_count: number;\n last_rejected_at: string | null;\n rejection_reason: string | null;\n}\n\nexport interface UsageIndex {\n version: 1;\n updated_at: string;\n by_id: Record<string, MemoryUsage>;\n}\n\nexport const USAGE_FILE = \"usage.json\";\n\nexport function emptyUsage(): MemoryUsage {\n return {\n read_count: 0,\n last_read_at: null,\n rejected_count: 0,\n last_rejected_at: null,\n rejection_reason: null,\n };\n}\n\nexport function emptyUsageIndex(): UsageIndex {\n return {\n version: 1,\n updated_at: new Date().toISOString(),\n by_id: {},\n };\n}\n\nexport function usagePath(paths: HaivePaths): string {\n return path.join(paths.haiveDir, \".cache\", USAGE_FILE);\n}\n\nexport async function loadUsageIndex(paths: HaivePaths): Promise<UsageIndex> {\n const file = usagePath(paths);\n if (!existsSync(file)) return emptyUsageIndex();\n const raw = await readFile(file, \"utf8\");\n try {\n const parsed = JSON.parse(raw) as UsageIndex;\n if (parsed.version !== 1) return emptyUsageIndex();\n return parsed;\n } catch {\n return emptyUsageIndex();\n }\n}\n\nexport async function saveUsageIndex(paths: HaivePaths, index: UsageIndex): Promise<void> {\n const file = usagePath(paths);\n await mkdir(path.dirname(file), { recursive: true });\n index.updated_at = new Date().toISOString();\n await writeFile(file, JSON.stringify(index, null, 2), \"utf8\");\n}\n\nexport function getUsage(index: UsageIndex, id: string): MemoryUsage {\n return index.by_id[id] ?? emptyUsage();\n}\n\nexport function bumpRead(index: UsageIndex, ids: string[]): UsageIndex {\n if (ids.length === 0) return index;\n const now = new Date().toISOString();\n for (const id of ids) {\n const current = index.by_id[id] ?? emptyUsage();\n index.by_id[id] = {\n ...current,\n read_count: current.read_count + 1,\n last_read_at: now,\n };\n }\n return index;\n}\n\nexport function recordRejection(\n index: UsageIndex,\n id: string,\n reason: string | null,\n): UsageIndex {\n const current = index.by_id[id] ?? emptyUsage();\n const now = new Date().toISOString();\n index.by_id[id] = {\n ...current,\n rejected_count: current.rejected_count + 1,\n last_rejected_at: now,\n rejection_reason: reason,\n };\n return index;\n}\n\nexport const DECAY_DAYS = 90;\n\nexport function isDecaying(usage: MemoryUsage, createdAt: string): boolean {\n const threshold = Date.now() - DECAY_DAYS * 24 * 60 * 60 * 1000;\n const anchor = usage.last_read_at ?? createdAt;\n return new Date(anchor).getTime() < threshold;\n}\n\nexport async function trackReads(\n paths: HaivePaths,\n ids: string[],\n): Promise<UsageIndex> {\n if (ids.length === 0) {\n return await loadUsageIndex(paths);\n }\n const index = await loadUsageIndex(paths);\n bumpRead(index, ids);\n await saveUsageIndex(paths, index);\n return index;\n}\n","import type { MemoryFrontmatter } from \"./types.js\";\nimport type { MemoryUsage } from \"./usage.js\";\n\nexport type ConfidenceLevel =\n | \"unverified\"\n | \"low\"\n | \"trusted\"\n | \"authoritative\"\n | \"stale\";\n\nexport interface ConfidenceThresholds {\n trustedReads: number;\n authoritativeReads: number;\n}\n\nexport const DEFAULT_CONFIDENCE_THRESHOLDS: ConfidenceThresholds = {\n trustedReads: 3,\n authoritativeReads: 10,\n};\n\nexport function deriveConfidence(\n fm: MemoryFrontmatter,\n usage: MemoryUsage,\n thresholds: ConfidenceThresholds = DEFAULT_CONFIDENCE_THRESHOLDS,\n): ConfidenceLevel {\n if (fm.status === \"stale\" || fm.status === \"deprecated\" || fm.status === \"rejected\") return \"stale\";\n if (fm.status === \"validated\") {\n return usage.read_count >= thresholds.authoritativeReads\n ? \"authoritative\"\n : \"trusted\";\n }\n if (fm.status === \"proposed\") {\n return usage.read_count >= thresholds.trustedReads ? \"trusted\" : \"low\";\n }\n // draft\n return \"unverified\";\n}\n\nexport interface AutoPromoteRule {\n /** Minimum read_count to promote proposed → validated. */\n minReads: number;\n /** Maximum rejected_count tolerated (memories with more rejections never auto-promote). */\n maxRejections: number;\n}\n\nexport const DEFAULT_AUTO_PROMOTE_RULE: AutoPromoteRule = {\n minReads: 5,\n maxRejections: 0,\n};\n\nexport function isAutoPromoteEligible(\n fm: MemoryFrontmatter,\n usage: MemoryUsage,\n rule: AutoPromoteRule = DEFAULT_AUTO_PROMOTE_RULE,\n): boolean {\n if (fm.status !== \"proposed\") return false;\n if (usage.rejected_count > rule.maxRejections) return false;\n return usage.read_count >= rule.minReads;\n}\n","import path from \"node:path\";\nimport type { LoadedMemory } from \"./loader.js\";\n\nconst MODULE_PATTERNS = [\n /^packages\\/([^/]+)\\//,\n /^apps\\/([^/]+)\\//,\n /^modules\\/([^/]+)\\//,\n /^src\\/([^/]+)\\//,\n /^libs\\/([^/]+)\\//,\n /^services\\/([^/]+)\\//,\n /^internal\\/([^/]+)\\//,\n /^projects\\/([^/]+)\\//, // Nx layout\n /^cmd\\/([^/]+)\\//, // Go-style\n];\n\n/**\n * Best-effort inference: given a list of file paths, infer module names from\n * conventional layouts (packages/X/, apps/X/, modules/X/, src/X/).\n */\nexport function inferModulesFromPaths(filePaths: string[]): string[] {\n const out = new Set<string>();\n for (const p of filePaths) {\n const norm = normalize(p);\n for (const re of MODULE_PATTERNS) {\n const m = norm.match(re);\n if (m && m[1]) out.add(m[1]);\n }\n }\n return [...out].sort();\n}\n\n/**\n * Path overlap: returns true if `a` and `b` refer to the same path or one is a\n * parent of the other. Both inputs are treated as POSIX-style relative paths.\n */\nexport function pathsOverlap(a: string, b: string): boolean {\n const na = normalize(a);\n const nb = normalize(b);\n if (na === nb) return true;\n return na.startsWith(nb + \"/\") || nb.startsWith(na + \"/\");\n}\n\nexport function memoryMatchesAnchorPaths(\n memory: LoadedMemory[\"memory\"],\n inputPaths: string[],\n): boolean {\n const anchorPaths = memory.frontmatter.anchor.paths;\n if (anchorPaths.length === 0) return false;\n for (const ap of anchorPaths) {\n for (const ip of inputPaths) {\n if (pathsOverlap(ap, ip)) return true;\n }\n }\n return false;\n}\n\nfunction normalize(p: string): string {\n // Strip leading \"./\" and trailing \"/\", normalize separators.\n return p.replace(/\\\\/g, \"/\").replace(/^\\.\\//, \"\").replace(/\\/+$/, \"\");\n}\n\nexport function relPathFrom(root: string, abs: string): string {\n return path.relative(root, abs).replace(/\\\\/g, \"/\");\n}\n","/**\n * Token budgeting helpers. We use the standard heuristic of ~4 chars per token,\n * which is conservative for English/code/markdown. Callers that need exact\n * counts should plug in a real tokenizer; this module only ever over-estimates,\n * so the user's hard limits are respected.\n */\n\nexport const CHARS_PER_TOKEN = 4;\n\nexport function estimateTokens(text: string): number {\n return Math.ceil(text.length / CHARS_PER_TOKEN);\n}\n\nexport interface TruncateOptions {\n /** Maximum tokens allowed in the result (inclusive). */\n maxTokens: number;\n /** Marker inserted where content was dropped. */\n marker?: string;\n /** Where to keep characters from when truncating. Default: head. */\n mode?: \"head\" | \"tail\" | \"middle\";\n}\n\nexport interface TruncateResult {\n text: string;\n truncated: boolean;\n estimatedTokens: number;\n originalTokens: number;\n}\n\nconst DEFAULT_MARKER = \"\\n…[truncated]…\\n\";\n\nexport function truncateToTokens(\n input: string,\n options: TruncateOptions,\n): TruncateResult {\n const originalTokens = estimateTokens(input);\n const max = Math.max(0, options.maxTokens);\n if (originalTokens <= max) {\n return { text: input, truncated: false, estimatedTokens: originalTokens, originalTokens };\n }\n\n if (max === 0) {\n return { text: \"\", truncated: true, estimatedTokens: 0, originalTokens };\n }\n\n const marker = options.marker ?? DEFAULT_MARKER;\n const mode = options.mode ?? \"head\";\n const markerTokens = estimateTokens(marker);\n const budgetChars = Math.max(0, (max - markerTokens) * CHARS_PER_TOKEN);\n\n let result: string;\n if (budgetChars === 0) {\n result = \"\";\n } else if (mode === \"tail\") {\n result = marker + input.slice(input.length - budgetChars);\n } else if (mode === \"middle\") {\n const half = Math.floor(budgetChars / 2);\n result = input.slice(0, half) + marker + input.slice(input.length - half);\n } else {\n result = input.slice(0, budgetChars) + marker;\n }\n\n return {\n text: result,\n truncated: true,\n estimatedTokens: estimateTokens(result),\n originalTokens,\n };\n}\n\n/**\n * Allocate a global token budget across N parts with relative weights, then\n * truncate each part to its share. Returns parts in input order, paired with\n * truncate metadata.\n */\nexport interface BudgetPart {\n key: string;\n text: string;\n weight: number;\n mode?: TruncateOptions[\"mode\"];\n}\n\nexport interface BudgetSlice {\n key: string;\n text: string;\n truncated: boolean;\n estimatedTokens: number;\n originalTokens: number;\n allocatedTokens: number;\n}\n\nexport function allocateBudget(\n parts: BudgetPart[],\n maxTokens: number,\n): BudgetSlice[] {\n if (parts.length === 0) return [];\n const totalWeight = parts.reduce((s, p) => s + Math.max(0, p.weight), 0);\n if (totalWeight === 0) {\n return parts.map((p) => ({\n key: p.key,\n text: \"\",\n truncated: estimateTokens(p.text) > 0,\n estimatedTokens: 0,\n originalTokens: estimateTokens(p.text),\n allocatedTokens: 0,\n }));\n }\n\n // First pass: allocate by weight, but if a part's content fits in less than\n // its share, redistribute the surplus to others proportionally.\n const allocations = new Map<string, number>();\n let remaining = maxTokens;\n let remainingWeight = totalWeight;\n\n // Sort parts by share fit ascending so small ones consume their share first.\n const sortedByFit = [...parts]\n .map((p) => ({\n key: p.key,\n tokens: estimateTokens(p.text),\n share: (p.weight / totalWeight) * maxTokens,\n part: p,\n }))\n .sort((a, b) => a.tokens - b.tokens);\n\n for (const item of sortedByFit) {\n const myShare = remainingWeight > 0\n ? (item.part.weight / remainingWeight) * remaining\n : 0;\n const grant = Math.min(item.tokens, Math.floor(myShare));\n allocations.set(item.key, grant);\n remaining -= grant;\n remainingWeight -= item.part.weight;\n }\n\n return parts.map((p) => {\n const allocated = allocations.get(p.key) ?? 0;\n const truncated = truncateToTokens(p.text, {\n maxTokens: allocated,\n mode: p.mode ?? \"head\",\n });\n return {\n key: p.key,\n text: truncated.text,\n truncated: truncated.truncated,\n estimatedTokens: truncated.estimatedTokens,\n originalTokens: truncated.originalTokens,\n allocatedTokens: allocated,\n };\n });\n}\n","import { mkdir, readFile, readdir, writeFile } from \"node:fs/promises\";\nimport { existsSync } from \"node:fs\";\nimport path from \"node:path\";\nimport type { HaivePaths } from \"./paths.js\";\n\nexport const CODE_MAP_FILE = \"code-map.json\";\n\nexport type CodeExportKind =\n | \"function\"\n | \"class\"\n | \"interface\"\n | \"type\"\n | \"const\"\n | \"enum\"\n | \"default\";\n\nexport interface CodeExport {\n name: string;\n kind: CodeExportKind;\n description?: string;\n line: number;\n}\n\nexport interface CodeFileEntry {\n summary?: string;\n exports: CodeExport[];\n loc: number;\n}\n\nexport interface CodeMap {\n version: 1;\n generated_at: string;\n root: string;\n files: Record<string, CodeFileEntry>;\n}\n\nexport interface BuildCodeMapOptions {\n includeExtensions?: string[];\n excludeDirs?: string[];\n}\n\nconst DEFAULT_INCLUDE = [\n \".ts\", \".tsx\", \".js\", \".jsx\", \".mjs\", \".cjs\",\n \".java\", \".kt\",\n \".py\",\n \".go\",\n \".rb\",\n \".rs\",\n \".cs\",\n \".php\",\n];\nconst DEFAULT_EXCLUDE = [\n \"node_modules\",\n \"dist\",\n \"build\",\n \"out\",\n \".git\",\n \".next\",\n \".turbo\",\n \".vitest-cache\",\n \"coverage\",\n \"test\",\n \"tests\",\n \"__tests__\",\n \"__mocks__\",\n \"target\", // Maven/Gradle build output\n \".gradle\",\n \"__pycache__\",\n \".pytest_cache\",\n \"vendor\", // Go / PHP\n];\n\nconst TEST_FILE_RE = /\\.(test|spec)\\.[a-z]+$/i;\n\nexport function codeMapPath(paths: HaivePaths): string {\n return path.join(paths.haiveDir, CODE_MAP_FILE);\n}\n\nexport async function loadCodeMap(paths: HaivePaths): Promise<CodeMap | null> {\n const file = codeMapPath(paths);\n if (!existsSync(file)) return null;\n return JSON.parse(await readFile(file, \"utf8\")) as CodeMap;\n}\n\nexport async function saveCodeMap(paths: HaivePaths, map: CodeMap): Promise<void> {\n const file = codeMapPath(paths);\n await mkdir(path.dirname(file), { recursive: true });\n await writeFile(file, JSON.stringify(map, null, 2), \"utf8\");\n}\n\nexport async function buildCodeMap(\n root: string,\n options: BuildCodeMapOptions = {},\n): Promise<CodeMap> {\n const include = new Set(options.includeExtensions ?? DEFAULT_INCLUDE);\n const exclude = new Set(options.excludeDirs ?? DEFAULT_EXCLUDE);\n const files: Record<string, CodeFileEntry> = {};\n\n for await (const abs of walkSourceFiles(root, include, exclude)) {\n const rel = path.relative(root, abs).replace(/\\\\/g, \"/\");\n if (rel.startsWith(\".ai/\")) continue;\n const content = await readFile(abs, \"utf8\");\n const ext = path.extname(abs).toLowerCase();\n const entry = parseFile(content, ext);\n if (entry.exports.length > 0) files[rel] = entry;\n }\n\n return {\n version: 1,\n generated_at: new Date().toISOString(),\n root,\n files,\n };\n}\n\nasync function* walkSourceFiles(\n dir: string,\n include: Set<string>,\n exclude: Set<string>,\n): AsyncGenerator<string> {\n let entries;\n try {\n entries = await readdir(dir, { withFileTypes: true });\n } catch {\n return;\n }\n for (const entry of entries) {\n if (entry.name.startsWith(\".\") && entry.name !== \".github\") {\n // Skip hidden dirs except .github (workflows can be useful)\n if (entry.isDirectory()) continue;\n }\n if (exclude.has(entry.name)) continue;\n const full = path.join(dir, entry.name);\n if (entry.isDirectory()) {\n yield* walkSourceFiles(full, include, exclude);\n } else if (entry.isFile()) {\n const ext = path.extname(entry.name).toLowerCase();\n if (include.has(ext) && !TEST_FILE_RE.test(entry.name)) yield full;\n }\n }\n}\n\nconst EXPORT_RE =\n /^export\\s+(?:default\\s+)?(async\\s+)?(function|class|interface|type|const|let|var|enum)\\s+(\\*?)\\s*([A-Za-z_$][\\w$]*)/gm;\n\nconst NAMED_REEXPORT_RE = /^export\\s*\\{([^}]+)\\}/gm;\n\nconst FILE_HEADER_COMMENT_RE = /^\\/\\*\\*([\\s\\S]*?)\\*\\//;\n\n// Java / Kotlin: public/protected class, interface, enum, record, @interface, fun, @RestController etc.\nconst JAVA_DECL_RE =\n /^(?:[ \\t]*)(?:@\\w+\\s+)*(?:public|protected|private|internal)?\\s*(?:static\\s+|final\\s+|abstract\\s+|open\\s+|data\\s+|sealed\\s+)*(?:(class|interface|enum|record|@interface|object)\\s+([A-Z][A-Za-z0-9_$]*)|(fun|def|func|function)\\s+([a-z_][A-Za-z0-9_$]*))/gm;\n\n// Python: def / class at module level (not indented)\nconst PYTHON_DECL_RE = /^(def|class)\\s+([A-Za-z_][A-Za-z0-9_]*)/gm;\n\n// Go: func declarations\nconst GO_DECL_RE = /^func\\s+(?:\\(\\w+\\s+\\*?[A-Za-z_][\\w]*\\)\\s+)?([A-Za-z_][A-Za-z0-9_]*)/gm;\n\n// Rust: pub fn / pub struct / pub enum / pub trait\nconst RUST_DECL_RE =\n /^pub(?:\\([^)]*\\))?\\s+(fn|struct|enum|trait|type|const|impl|mod)\\s+([A-Za-z_][A-Za-z0-9_]*)/gm;\n\nfunction parseFile(source: string, ext: string): CodeFileEntry {\n if (ext === \".java\" || ext === \".kt\") return parseJvmFile(source);\n if (ext === \".py\") return parsePythonFile(source);\n if (ext === \".go\") return parseGoFile(source);\n if (ext === \".rs\") return parseRustFile(source);\n return parseJsFile(source);\n}\n\nfunction parseJsFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n\n let m: RegExpExecArray | null;\n EXPORT_RE.lastIndex = 0;\n while ((m = EXPORT_RE.exec(source))) {\n const kindRaw = m[2] ?? \"\";\n const name = m[4] ?? \"\";\n if (!name) continue;\n const kind: CodeExportKind =\n kindRaw === \"function\" ? \"function\" :\n kindRaw === \"class\" ? \"class\" :\n kindRaw === \"interface\" ? \"interface\" :\n kindRaw === \"type\" ? \"type\" :\n kindRaw === \"enum\" ? \"enum\" : \"const\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n\n NAMED_REEXPORT_RE.lastIndex = 0;\n while ((m = NAMED_REEXPORT_RE.exec(source))) {\n const inside = m[1] ?? \"\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n for (const part of inside.split(\",\")) {\n const cleaned = part.trim().split(/\\s+as\\s+/).pop()?.trim() ?? \"\";\n if (!cleaned || cleaned.startsWith(\"type \")) continue;\n if (exports.some((e) => e.name === cleaned)) continue;\n exports.push({ name: cleaned, kind: \"const\", line: lineIdx + 1 });\n }\n }\n\n const summary = extractFileSummary(source);\n return { ...(summary ? { summary } : {}), exports, loc: source.split(\"\\n\").length };\n}\n\nfunction parseJvmFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n JAVA_DECL_RE.lastIndex = 0;\n while ((m = JAVA_DECL_RE.exec(source))) {\n const kindRaw = m[1] ?? m[3] ?? \"\";\n const name = m[2] ?? m[4] ?? \"\";\n if (!name) continue;\n const kind: CodeExportKind =\n kindRaw === \"class\" || kindRaw === \"record\" || kindRaw === \"object\" ? \"class\" :\n kindRaw === \"interface\" || kindRaw === \"@interface\" ? \"interface\" :\n kindRaw === \"enum\" ? \"enum\" :\n kindRaw === \"fun\" || kindRaw === \"def\" || kindRaw === \"func\" || kindRaw === \"function\" ? \"function\" :\n \"const\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n const summary = extractJavaSummary(source);\n return { ...(summary ? { summary } : {}), exports, loc: lines.length };\n}\n\nfunction parsePythonFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n PYTHON_DECL_RE.lastIndex = 0;\n while ((m = PYTHON_DECL_RE.exec(source))) {\n const keyword = m[1] ?? \"\";\n const name = m[2] ?? \"\";\n if (!name || name.startsWith(\"_\")) continue;\n const kind: CodeExportKind = keyword === \"class\" ? \"class\" : \"function\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractPythonDocstring(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n const summary = extractPythonModuleDocstring(source);\n return { ...(summary ? { summary } : {}), exports, loc: lines.length };\n}\n\nfunction parseGoFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n GO_DECL_RE.lastIndex = 0;\n while ((m = GO_DECL_RE.exec(source))) {\n const name = m[1] ?? \"\";\n if (!name || !/^[A-Z]/.test(name)) continue; // Only exported (uppercase) in Go\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind: \"function\", ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n return { exports, loc: lines.length };\n}\n\nfunction parseRustFile(source: string): CodeFileEntry {\n const exports: CodeExport[] = [];\n const lines = source.split(\"\\n\");\n const lineOffsets = computeLineOffsets(source);\n let m: RegExpExecArray | null;\n RUST_DECL_RE.lastIndex = 0;\n while ((m = RUST_DECL_RE.exec(source))) {\n const kindRaw = m[1] ?? \"\";\n const name = m[2] ?? \"\";\n if (!name) continue;\n const kind: CodeExportKind =\n kindRaw === \"struct\" || kindRaw === \"impl\" ? \"class\" :\n kindRaw === \"enum\" ? \"enum\" :\n kindRaw === \"trait\" ? \"interface\" :\n kindRaw === \"fn\" ? \"function\" :\n kindRaw === \"type\" ? \"type\" : \"const\";\n const lineIdx = byteToLine(m.index, lineOffsets);\n const description = extractJSDocAbove(lines, lineIdx);\n exports.push({ name, kind, ...(description ? { description } : {}), line: lineIdx + 1 });\n }\n return { exports, loc: lines.length };\n}\n\nfunction extractJavaSummary(source: string): string | undefined {\n // Java/Kotlin: file-level Javadoc before first class/interface\n const m = source.match(/^\\/\\*\\*([\\s\\S]*?)\\*\\//);\n if (!m) return undefined;\n const block = (m[1] ?? \"\")\n .split(\"\\n\")\n .map((l) => l.replace(/^\\s*\\*\\s?/, \"\").trim())\n .filter((l) => l && !l.startsWith(\"@\"))\n .join(\" \");\n return block ? firstSentence(block) : undefined;\n}\n\nfunction extractPythonDocstring(lines: string[], defLine: number): string | undefined {\n const next = lines[defLine + 1] ?? \"\";\n const stripped = next.trim();\n if (stripped.startsWith('\"\"\"') || stripped.startsWith(\"'''\")) {\n const inner = stripped.replace(/^[\"']{3}/, \"\").replace(/[\"']{3}.*$/, \"\").trim();\n return inner || undefined;\n }\n return undefined;\n}\n\nfunction extractPythonModuleDocstring(source: string): string | undefined {\n const m = source.match(/^[\"']{3}([\\s\\S]*?)[\"']{3}/);\n if (!m) return undefined;\n return firstSentence((m[1] ?? \"\").trim());\n}\n\nfunction computeLineOffsets(source: string): number[] {\n const out: number[] = [0];\n for (let i = 0; i < source.length; i++) {\n if (source[i] === \"\\n\") out.push(i + 1);\n }\n return out;\n}\n\nfunction byteToLine(byte: number, offsets: number[]): number {\n let lo = 0;\n let hi = offsets.length - 1;\n while (lo < hi) {\n const mid = (lo + hi + 1) >> 1;\n const off = offsets[mid] ?? 0;\n if (off <= byte) lo = mid;\n else hi = mid - 1;\n }\n return lo;\n}\n\nfunction extractJSDocAbove(lines: string[], exportLine: number): string | undefined {\n let i = exportLine - 1;\n // Skip blank lines between JSDoc and export\n while (i >= 0 && (lines[i] ?? \"\").trim() === \"\") i--;\n if (i < 0) return undefined;\n const line = (lines[i] ?? \"\").trim();\n\n if (line.startsWith(\"//\")) {\n return line.replace(/^\\/\\/\\s*/, \"\").trim() || undefined;\n }\n\n // Single-line JSDoc: /** Adds two numbers. */\n const singleLine = line.match(/^\\/\\*\\*\\s*(.*?)\\s*\\*\\/\\s*$/);\n if (singleLine && singleLine[1]) {\n return firstSentence(singleLine[1]);\n }\n\n if (line.endsWith(\"*/\")) {\n // Walk up until /**\n const collected: string[] = [];\n // First piece: content of the line before */\n const firstPiece = line.replace(/\\*\\/\\s*$/, \"\").replace(/^\\*\\s?/, \"\").trim();\n if (firstPiece) collected.unshift(firstPiece);\n let j = i - 1;\n while (j >= 0) {\n const l = (lines[j] ?? \"\").trim();\n if (l.startsWith(\"/**\")) {\n const inner = l.replace(/^\\/\\*\\*/, \"\").trim();\n if (inner) collected.unshift(inner);\n break;\n }\n collected.unshift(l.replace(/^\\*\\s?/, \"\").trim());\n j--;\n }\n const joined = collected.join(\" \").trim();\n if (!joined) return undefined;\n return firstSentence(joined);\n }\n return undefined;\n}\n\nfunction firstSentence(text: string): string | undefined {\n const trimmed = text.trim();\n if (!trimmed) return undefined;\n return trimmed.split(/(?<=\\.)\\s+/)[0]?.trim();\n}\n\nfunction extractFileSummary(source: string): string | undefined {\n const m = source.match(FILE_HEADER_COMMENT_RE);\n if (!m) return undefined;\n const block = (m[1] ?? \"\")\n .split(\"\\n\")\n .map((l) => l.replace(/^\\s*\\*\\s?/, \"\").trim())\n .filter(Boolean)\n .join(\" \");\n if (!block) return undefined;\n const sentence = block.split(/(?<=\\.)\\s+/)[0]?.trim();\n return sentence;\n}\n\nexport interface CodeMapQueryOptions {\n file?: string;\n symbol?: string;\n}\n\nexport function queryCodeMap(map: CodeMap, options: CodeMapQueryOptions): {\n files: Array<{ path: string; entry: CodeFileEntry }>;\n} {\n const files: Array<{ path: string; entry: CodeFileEntry }> = [];\n for (const [filePath, entry] of Object.entries(map.files)) {\n if (options.file) {\n if (!filePath.includes(options.file)) continue;\n }\n if (options.symbol) {\n const sym = options.symbol.toLowerCase();\n if (!entry.exports.some((e) => e.name.toLowerCase().includes(sym))) continue;\n }\n files.push({ path: filePath, entry });\n }\n return { files };\n}\n"],"mappings":"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","names":["path","path","readFile","readdir","existsSync","path","readFile","existsSync","path","path","mkdir","readFile","readdir","writeFile","existsSync","path"]}
|