@llangtop/pwiki-core 0.4.6 → 1.0.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 (137) hide show
  1. package/dist/WikiEngine.d.ts +21 -24
  2. package/dist/WikiEngine.d.ts.map +1 -1
  3. package/dist/WikiEngine.js +251 -144
  4. package/dist/WikiEngine.js.map +1 -1
  5. package/dist/config.d.ts +18 -0
  6. package/dist/config.d.ts.map +1 -0
  7. package/dist/config.js +61 -0
  8. package/dist/config.js.map +1 -0
  9. package/dist/index.d.ts +16 -17
  10. package/dist/index.d.ts.map +1 -1
  11. package/dist/index.js +22 -25
  12. package/dist/index.js.map +1 -1
  13. package/dist/lib/ast-chunker.d.ts.map +1 -0
  14. package/dist/{ast-chunker.js → lib/ast-chunker.js} +2 -2
  15. package/dist/lib/ast-chunker.js.map +1 -0
  16. package/dist/lib/content-cache.d.ts.map +1 -0
  17. package/dist/lib/content-cache.js.map +1 -0
  18. package/dist/{embedder.d.ts → lib/embedder.d.ts} +0 -16
  19. package/dist/lib/embedder.d.ts.map +1 -0
  20. package/dist/{embedder.js → lib/embedder.js} +21 -98
  21. package/dist/lib/embedder.js.map +1 -0
  22. package/dist/{file-manifest.d.ts → lib/file-manifest.d.ts} +0 -10
  23. package/dist/lib/file-manifest.d.ts.map +1 -0
  24. package/dist/{file-manifest.js → lib/file-manifest.js} +9 -50
  25. package/dist/lib/file-manifest.js.map +1 -0
  26. package/dist/{indexer-compile.d.ts → lib/indexer-compile.d.ts} +5 -7
  27. package/dist/lib/indexer-compile.d.ts.map +1 -0
  28. package/dist/{indexer-compile.js → lib/indexer-compile.js} +12 -13
  29. package/dist/lib/indexer-compile.js.map +1 -0
  30. package/dist/{indexer-embed.d.ts → lib/indexer-embed.d.ts} +3 -5
  31. package/dist/lib/indexer-embed.d.ts.map +1 -0
  32. package/dist/{indexer-embed.js → lib/indexer-embed.js} +15 -16
  33. package/dist/lib/indexer-embed.js.map +1 -0
  34. package/dist/lib/indexer-scan.d.ts.map +1 -0
  35. package/dist/lib/indexer-scan.js.map +1 -0
  36. package/dist/lib/indexer.d.ts.map +1 -0
  37. package/dist/lib/indexer.js.map +1 -0
  38. package/dist/lib/model-registry.d.ts +18 -0
  39. package/dist/lib/model-registry.d.ts.map +1 -0
  40. package/dist/lib/model-registry.js +52 -0
  41. package/dist/lib/model-registry.js.map +1 -0
  42. package/dist/lib/parser.d.ts.map +1 -0
  43. package/dist/lib/parser.js.map +1 -0
  44. package/dist/lib/preprocessor.d.ts.map +1 -0
  45. package/dist/lib/preprocessor.js.map +1 -0
  46. package/dist/{search.d.ts → lib/search.d.ts} +0 -2
  47. package/dist/lib/search.d.ts.map +1 -0
  48. package/dist/{search.js → lib/search.js} +12 -38
  49. package/dist/lib/search.js.map +1 -0
  50. package/dist/{semantic-compiler.d.ts → lib/semantic-compiler.d.ts} +2 -2
  51. package/dist/lib/semantic-compiler.d.ts.map +1 -0
  52. package/dist/lib/semantic-compiler.js.map +1 -0
  53. package/dist/lib/semantic-search.d.ts +4 -0
  54. package/dist/lib/semantic-search.d.ts.map +1 -0
  55. package/dist/{semantic-search.js → lib/semantic-search.js} +22 -82
  56. package/dist/lib/semantic-search.js.map +1 -0
  57. package/dist/lib/store-config.d.ts +25 -0
  58. package/dist/lib/store-config.d.ts.map +1 -0
  59. package/dist/lib/store-config.js +85 -0
  60. package/dist/lib/store-config.js.map +1 -0
  61. package/dist/lib/store-index.d.ts +14 -0
  62. package/dist/lib/store-index.d.ts.map +1 -0
  63. package/dist/lib/store-index.js +72 -0
  64. package/dist/lib/store-index.js.map +1 -0
  65. package/dist/lib/store-vectors.d.ts.map +1 -0
  66. package/dist/{store-vectors.js → lib/store-vectors.js} +7 -18
  67. package/dist/lib/store-vectors.js.map +1 -0
  68. package/dist/lib/store.d.ts +11 -0
  69. package/dist/lib/store.d.ts.map +1 -0
  70. package/dist/lib/store.js +22 -0
  71. package/dist/lib/store.js.map +1 -0
  72. package/dist/{types.d.ts → lib/types.d.ts} +17 -23
  73. package/dist/lib/types.d.ts.map +1 -0
  74. package/dist/lib/types.js +3 -0
  75. package/dist/lib/types.js.map +1 -0
  76. package/package.json +33 -37
  77. package/dist/ast-chunker.d.ts.map +0 -1
  78. package/dist/ast-chunker.js.map +0 -1
  79. package/dist/content-cache.d.ts.map +0 -1
  80. package/dist/content-cache.js.map +0 -1
  81. package/dist/embedder.d.ts.map +0 -1
  82. package/dist/embedder.js.map +0 -1
  83. package/dist/file-manifest.d.ts.map +0 -1
  84. package/dist/file-manifest.js.map +0 -1
  85. package/dist/indexer-compile.d.ts.map +0 -1
  86. package/dist/indexer-compile.js.map +0 -1
  87. package/dist/indexer-embed.d.ts.map +0 -1
  88. package/dist/indexer-embed.js.map +0 -1
  89. package/dist/indexer-scan.d.ts.map +0 -1
  90. package/dist/indexer-scan.js.map +0 -1
  91. package/dist/indexer.d.ts.map +0 -1
  92. package/dist/indexer.js.map +0 -1
  93. package/dist/model-registry.d.ts +0 -32
  94. package/dist/model-registry.d.ts.map +0 -1
  95. package/dist/model-registry.js +0 -82
  96. package/dist/model-registry.js.map +0 -1
  97. package/dist/parser.d.ts.map +0 -1
  98. package/dist/parser.js.map +0 -1
  99. package/dist/preprocessor.d.ts.map +0 -1
  100. package/dist/preprocessor.js.map +0 -1
  101. package/dist/search.d.ts.map +0 -1
  102. package/dist/search.js.map +0 -1
  103. package/dist/semantic-compiler.d.ts.map +0 -1
  104. package/dist/semantic-compiler.js.map +0 -1
  105. package/dist/semantic-search.d.ts +0 -11
  106. package/dist/semantic-search.d.ts.map +0 -1
  107. package/dist/semantic-search.js.map +0 -1
  108. package/dist/store-settings.d.ts +0 -32
  109. package/dist/store-settings.d.ts.map +0 -1
  110. package/dist/store-settings.js +0 -138
  111. package/dist/store-settings.js.map +0 -1
  112. package/dist/store-vectors.d.ts.map +0 -1
  113. package/dist/store-vectors.js.map +0 -1
  114. package/dist/store.d.ts +0 -11
  115. package/dist/store.d.ts.map +0 -1
  116. package/dist/store.js +0 -28
  117. package/dist/store.js.map +0 -1
  118. package/dist/types.d.ts.map +0 -1
  119. package/dist/types.js +0 -3
  120. package/dist/types.js.map +0 -1
  121. package/dist/wiki-paths.d.ts +0 -3
  122. package/dist/wiki-paths.d.ts.map +0 -1
  123. package/dist/wiki-paths.js +0 -13
  124. package/dist/wiki-paths.js.map +0 -1
  125. /package/dist/{ast-chunker.d.ts → lib/ast-chunker.d.ts} +0 -0
  126. /package/dist/{content-cache.d.ts → lib/content-cache.d.ts} +0 -0
  127. /package/dist/{content-cache.js → lib/content-cache.js} +0 -0
  128. /package/dist/{indexer-scan.d.ts → lib/indexer-scan.d.ts} +0 -0
  129. /package/dist/{indexer-scan.js → lib/indexer-scan.js} +0 -0
  130. /package/dist/{indexer.d.ts → lib/indexer.d.ts} +0 -0
  131. /package/dist/{indexer.js → lib/indexer.js} +0 -0
  132. /package/dist/{parser.d.ts → lib/parser.d.ts} +0 -0
  133. /package/dist/{parser.js → lib/parser.js} +0 -0
  134. /package/dist/{preprocessor.d.ts → lib/preprocessor.d.ts} +0 -0
  135. /package/dist/{preprocessor.js → lib/preprocessor.js} +0 -0
  136. /package/dist/{semantic-compiler.js → lib/semantic-compiler.js} +0 -0
  137. /package/dist/{store-vectors.d.ts → lib/store-vectors.d.ts} +0 -0
@@ -1,19 +1,15 @@
1
- // search.ts — 关键词搜索 (v5.0)
2
- // 标题/路径/标签/内容匹配 行级上下文展示
3
- import { getIndex } from "./store.js";
4
- import { readFileSync } from "node:fs";
5
- import { resolve as resolvePath } from "node:path";
1
+ // search.ts — 关键词搜索
2
+ // 适配自 extensions/wiki/lib/search.ts — 导入改为 store-index + content-cache
3
+ import { getIndex } from "./store-index.js";
6
4
  import { getContent } from "./content-cache.js";
7
- /** 提取匹配行的上下文(前一行、匹配行、后一行) */
8
5
  function lineContext(content, query, maxLen = 100) {
9
6
  const lower = content.toLowerCase();
10
7
  const q = query.toLowerCase();
11
8
  const pos = lower.indexOf(q);
12
9
  if (pos < 0)
13
10
  return "";
14
- // 找到匹配位置所在行号
15
11
  const before = content.slice(0, pos);
16
- const lineNum = before.split("\n").length; // 1-indexed
12
+ const lineNum = before.split("\n").length;
17
13
  const lines = content.split("\n");
18
14
  const prev = lineNum > 1 ? lines[lineNum - 2].trim() : "";
19
15
  const curr = lines[lineNum - 1].trim();
@@ -26,7 +22,6 @@ function lineContext(content, query, maxLen = 100) {
26
22
  parts.push(`L${lineNum + 1}: ${next.slice(0, maxLen)}`);
27
23
  return parts.join("\n");
28
24
  }
29
- /** 关键词搜索(同步,纯子串匹配 + 加权打分) */
30
25
  export function keywordSearch(query) {
31
26
  const idx = getIndex();
32
27
  const q = query.toLowerCase();
@@ -34,28 +29,13 @@ export function keywordSearch(query) {
34
29
  for (const [relPath, entry] of Object.entries(idx)) {
35
30
  let score = 0;
36
31
  const parts = [];
37
- // 标题匹配
38
- if (entry.title.toLowerCase().includes(q)) {
32
+ if (entry.title.toLowerCase().includes(q))
39
33
  score += 10;
40
- }
41
- // 路径匹配
42
- if (relPath.toLowerCase().includes(q)) {
34
+ if (relPath.toLowerCase().includes(q))
43
35
  score += 5;
44
- }
45
- // 标签匹配
46
- if (entry.tags.some(t => t.toLowerCase().includes(q))) {
36
+ if (entry.tags.some(t => t.toLowerCase().includes(q)))
47
37
  score += 3;
48
- }
49
- // 内容匹配(优先内存缓存,miss 时回退磁盘)
50
- let content = getContent(relPath);
51
- if (!content) {
52
- try {
53
- content = readFileSync(resolvePath(entry.sourceDir, relPath), "utf-8");
54
- }
55
- catch {
56
- content = undefined;
57
- }
58
- }
38
+ const content = getContent(relPath);
59
39
  if (content) {
60
40
  const lower = content.toLowerCase();
61
41
  let count = 0, p = lower.indexOf(q);
@@ -63,29 +43,23 @@ export function keywordSearch(query) {
63
43
  count++;
64
44
  if (count === 1)
65
45
  score += 1;
66
- // 取该匹配位置的行上下文
67
46
  const ctx = lineContext(content, query);
68
47
  if (ctx && !parts.some(pp => pp.includes(ctx.slice(0, 30)))) {
69
48
  parts.push(ctx);
70
49
  }
71
50
  p = lower.indexOf(q, p + 1);
72
51
  }
73
- // 多次出现加分
74
52
  score += Math.min(count - 1, 9);
75
53
  }
76
54
  if (score > 0) {
77
55
  hits.push({
78
- relPath: entry.relPath,
79
- sourceDir: entry.sourceDir,
80
- title: entry.title,
81
- tags: entry.tags,
82
- snippet: parts.join("\n"),
83
- score,
56
+ relPath: entry.relPath, sourceDir: entry.sourceDir,
57
+ title: entry.title, tags: entry.tags,
58
+ snippet: parts.join("\n"), score,
84
59
  });
85
60
  }
86
61
  }
87
62
  return hits.sort((a, b) => b.score - a.score);
88
63
  }
89
- /** 向后兼容别名 */
90
- export const search = keywordSearch; // alias
64
+ export const search = keywordSearch;
91
65
  //# sourceMappingURL=search.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"search.js","sourceRoot":"","sources":["../../src/lib/search.ts"],"names":[],"mappings":"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"}
@@ -36,9 +36,9 @@ export declare function buildFileLLMPrompt(relPath: string, fullText: string): s
36
36
  /**
37
37
  * v5.4 解析文件级 LLM 响应(单对象,非 segments 数组)
38
38
  */
39
- export declare function parseFileLLMResult(text: string): import("./types.js").FileLLMData | null;
39
+ export declare function parseFileLLMResult(text: string): import("../lib/types.js").FileLLMData | null;
40
40
  /**
41
41
  * v5.4 构建文件级 LLM 向量的 embedding 文本
42
42
  */
43
- export declare function buildFileLLMEmbeddingText(data: import("./types.js").FileLLMData, relPath?: string, maxEmbedLen?: number): string;
43
+ export declare function buildFileLLMEmbeddingText(data: import("../lib/types.js").FileLLMData, relPath?: string, maxEmbedLen?: number): string;
44
44
  //# sourceMappingURL=semantic-compiler.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"semantic-compiler.d.ts","sourceRoot":"","sources":["../../src/lib/semantic-compiler.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAAE,QAAQ,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AACvE,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AAM3D,kCAAkC;AAClC,eAAO,MAAM,UAAU,KAAK,CAAC;AAM7B,eAAO,MAAM,qBAAqB,siDAyBT,CAAC;AAM1B,4BAA4B;AAC5B,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,QAAQ,EAAE,GAAG,MAAM,CAkG7D;AAMD;;;;;;;GAOG;AACH,wBAAgB,kBAAkB,CAChC,KAAK,EAAE,MAAM,EACb,cAAc,EAAE,MAAM,EACtB,QAAQ,EAAE,MAAM,EAAE,EAClB,OAAO,EAAE,MAAM,EAAE,EACjB,QAAQ,EAAE,MAAM,EAAE,EAClB,YAAY,EAAE,MAAM,EACpB,cAAc,EAAE,MAAM,GAAG,SAAS,EAClC,OAAO,EAAE,MAAM,GACd,MAAM,CAWR;AAMD,qCAAqC;AACrC,wBAAgB,mBAAmB,CACjC,IAAI,EAAE,MAAM,GACX,aAAa,EAAE,GAAG,IAAI,CAiBxB;AAMD,0CAA0C;AAC1C,eAAO,MAAM,0BAA0B,koDAgBL,CAAC;AAEnC;;;;;GAKG;AACH,wBAAgB,sBAAsB,CACpC,OAAO,EAAE,MAAM,EACf,QAAQ,EAAE,MAAM,EAChB,YAAY,EAAE,iBAAiB,EAAE,GAChC,MAAM,CAwCR;AAED,iCAAiC;AACjC,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,WAAW,EAAE,GAAG,IAAI,CAgBpE;AAMD,kCAAkC;AAClC,eAAO,MAAM,sBAAsB,u7CAgBD,CAAC;AAEnC;;GAEG;AACH,wBAAgB,kBAAkB,CAChC,OAAO,EAAE,MAAM,EACf,QAAQ,EAAE,MAAM,GACf,MAAM,CAmBR;AAED;;GAEG;AACH,wBAAgB,kBAAkB,CAChC,IAAI,EAAE,MAAM,GACX,OAAO,iBAAiB,EAAE,WAAW,GAAG,IAAI,CAyB9C;AAED;;GAEG;AACH,wBAAgB,yBAAyB,CAAC,IAAI,EAAE,OAAO,iBAAiB,EAAE,WAAW,EAAE,OAAO,CAAC,EAAE,MAAM,EAAE,WAAW,SAAO,GAAG,MAAM,CAYnI"}
@@ -0,0 +1 @@
1
+ {"version":3,"file":"semantic-compiler.js","sourceRoot":"","sources":["../../src/lib/semantic-compiler.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import type { SearchHit } from "./types.js";
2
+ export declare function semanticSearch(query: string): Promise<SearchHit[]>;
3
+ export declare function hybridSearch(query: string): Promise<SearchHit[]>;
4
+ //# sourceMappingURL=semantic-search.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"semantic-search.d.ts","sourceRoot":"","sources":["../../src/lib/semantic-search.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAAE,SAAS,EAAa,MAAM,YAAY,CAAC;AAoBvD,wBAAsB,cAAc,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC,CAqExE;AAmCD,wBAAsB,YAAY,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC,CAoCtE"}
@@ -1,31 +1,17 @@
1
- // semantic-search.ts — 语义搜索 & 混合搜索 (v5.1)
2
- //
3
- // semanticSearch: query embed 余弦相似度 → 同文件多块聚合加分
4
- // hybridSearch: 关键词 + 语义并行 RRF 融合排序 (k=60, Top-50)
5
- //
6
- // 策略:
7
- // 高阈值 0.50 — 只有置信度 ≥50% 的语义匹配才视为有效
8
- // 兜底 — 高阈值结果不足 3 条时,追加 ≤3 条低分结果(标记"弱匹配")
9
- // 同文件合并 — 一个文件多个块命中时,取最高块相似度 + (块数-1)*0.05 加分(上限 0.25)
10
- // RRF 融合 — 替代简单线性加权,对异构分数尺度不敏感
11
- import { getEmbeddings, getSemanticEnabled, getChunkInfo } from "./store.js";
12
- import { getIndex } from "./store.js";
1
+ // semantic-search.ts — 语义搜索 & 混合搜索
2
+ // 适配自 extensions/wiki/lib/semantic-search.ts — 导入拆分
3
+ import { getEmbeddings, getChunkInfo } from "./store-vectors.js";
4
+ import { getSemanticEnabled } from "./store-config.js";
5
+ import { getIndex } from "./store-index.js";
13
6
  import { embed, initialize, isAvailable, cosineSimilarity } from "./embedder.js";
14
7
  import { keywordSearch } from "./search.js";
15
- /** 高置信度阈值 — ≥50% 视为强匹配 */
16
8
  const HIGH_SIMILARITY_THRESHOLD = 0.50;
17
- /** 最低阈值 — 低于此值不展示(即使兜底) */
18
9
  const MIN_SIMILARITY_THRESHOLD = 0.20;
19
- /** 兜底条数 — 强匹配不足时最多追加几条弱匹配 */
20
10
  const FALLBACK_COUNT = 3;
21
- /** 多块加分:每额外一个命中块 +0.05,上限 0.25 */
22
11
  const MULTI_CHUNK_BONUS = 0.05;
23
12
  const MAX_MULTI_CHUNK_BONUS = 0.25;
24
- /** RRF 融合常数 (标准值 60) */
25
13
  const RRF_K = 60;
26
- /** 各列表参与 RRF 融合的 Top-N 上限 */
27
14
  const RRF_TOPN = 50;
28
- /** 纯语义搜索 */
29
15
  export async function semanticSearch(query) {
30
16
  if (!getSemanticEnabled())
31
17
  return [];
@@ -46,7 +32,6 @@ export async function semanticSearch(query) {
46
32
  catch {
47
33
  return [];
48
34
  }
49
- // 1. 计算所有块的相似度
50
35
  const allChunks = [];
51
36
  for (const [key, vec] of Object.entries(embeddings)) {
52
37
  const chunkMatch = key.match(/^(.*)###(\d+|llm)$/);
@@ -60,44 +45,34 @@ export async function semanticSearch(query) {
60
45
  continue;
61
46
  const ci = chunkIdx !== undefined ? chunkInfo[key] : undefined;
62
47
  allChunks.push({
63
- key,
64
- relPath,
65
- similarity,
66
- chunkIndex: chunkIdx,
48
+ key, relPath, similarity, chunkIndex: chunkIdx,
67
49
  chunkHeading: ci ? ci.heading.replace(/^#+\s*/, "") : undefined,
68
50
  });
69
51
  }
70
- // 2. 同文件聚合:取最高块 + 多块加分
71
52
  const fileMap = new Map();
72
53
  for (const ch of allChunks) {
73
54
  const existing = fileMap.get(ch.relPath);
74
55
  if (!existing) {
75
56
  fileMap.set(ch.relPath, {
76
- relPath: ch.relPath,
77
- semanticScore: ch.similarity,
78
- bestChunk: ch,
79
- chunkCount: 1,
57
+ relPath: ch.relPath, semanticScore: ch.similarity,
58
+ bestChunk: ch, chunkCount: 1,
80
59
  chunkHeadings: ch.chunkHeading ? [ch.chunkHeading] : [],
81
60
  });
82
61
  }
83
62
  else {
84
- // 追踪最高分块
85
- if (ch.similarity > existing.bestChunk.similarity) {
63
+ if (ch.similarity > existing.bestChunk.similarity)
86
64
  existing.bestChunk = ch;
87
- }
88
65
  existing.chunkCount++;
89
66
  if (ch.chunkHeading && !existing.chunkHeadings.includes(ch.chunkHeading)) {
90
67
  existing.chunkHeadings.push(ch.chunkHeading);
91
68
  }
92
69
  }
93
70
  }
94
- // 计算最终分数:最高块相似度 + 多块加分
95
71
  for (const fm of fileMap.values()) {
96
72
  const bonus = Math.min((fm.chunkCount - 1) * MULTI_CHUNK_BONUS, MAX_MULTI_CHUNK_BONUS);
97
73
  fm.semanticScore = fm.bestChunk.similarity + bonus;
98
74
  }
99
75
  const files = [...fileMap.values()].sort((a, b) => b.semanticScore - a.semanticScore);
100
- // 3. 强匹配(聚合后 ≥50%)/ 弱匹配兜底
101
76
  const strong = files.filter(f => f.semanticScore >= HIGH_SIMILARITY_THRESHOLD);
102
77
  const ci = getChunkInfo();
103
78
  const strongHits = strong.map(f => makeFileHit(f, idx, ci));
@@ -116,7 +91,6 @@ export async function semanticSearch(query) {
116
91
  }
117
92
  function makeFileHit(f, idx, chunkInfo) {
118
93
  const entry = idx[f.relPath];
119
- // 优先展示 LLM 编译结果(summary / topic),其次 AST 块标题
120
94
  let snippet = "";
121
95
  const llmKey = `${f.relPath}###llm`;
122
96
  const llm = chunkInfo?.[llmKey];
@@ -131,60 +105,33 @@ function makeFileHit(f, idx, chunkInfo) {
131
105
  else if (f.bestChunk.chunkHeading) {
132
106
  snippet = `▸ ${f.bestChunk.chunkHeading}`;
133
107
  }
134
- // 多块命中展示(最多 5 个附加标题)
135
108
  if (f.chunkCount > 1) {
136
- const others = f.chunkHeadings
137
- .filter(h => h !== f.bestChunk.chunkHeading)
138
- .slice(0, 5);
139
- if (others.length > 0) {
140
- snippet += ` | +${f.chunkCount - 1}块: ${others.join(", ")}`;
141
- }
142
- else {
143
- snippet += ` | +${f.chunkCount - 1}块命中`;
144
- }
109
+ const others = f.chunkHeadings.filter(h => h !== f.bestChunk.chunkHeading).slice(0, 5);
110
+ snippet += others.length > 0
111
+ ? ` | +${f.chunkCount - 1}块: ${others.join(", ")}`
112
+ : ` | +${f.chunkCount - 1}块命中`;
145
113
  }
146
114
  return {
147
- relPath: entry.relPath,
148
- sourceDir: entry.sourceDir,
149
- title: entry.title,
150
- tags: entry.tags,
151
- snippet,
115
+ relPath: entry.relPath, sourceDir: entry.sourceDir,
116
+ title: entry.title, tags: entry.tags, snippet,
152
117
  score: Math.round(f.semanticScore * 100),
153
118
  semanticScore: f.semanticScore,
154
119
  chunkIndex: f.bestChunk.chunkIndex,
155
120
  chunkHeading: f.bestChunk.chunkHeading,
156
121
  };
157
122
  }
158
- /** 混合搜索:关键词 + 语义并行 → RRF 融合排序
159
- *
160
- * RRF (Reciprocal Rank Fusion):
161
- * RRF(d) = Σ 1/(k + rank_i(d))
162
- * 各列表取 Top-N 参与融合,未出现在某列表中的项 rank = RRF_K*2
163
- */
164
123
  export async function hybridSearch(query) {
165
124
  const keywordHits = keywordSearch(query);
166
125
  const semanticHits = await semanticSearch(query);
167
- // 按分数排序并取 Top-N
168
- const kwSorted = [...keywordHits]
169
- .sort((a, b) => b.score - a.score)
170
- .slice(0, RRF_TOPN);
171
- const semSorted = [...semanticHits]
172
- .sort((a, b) => b.score - a.score)
173
- .slice(0, RRF_TOPN);
174
- // 构建 rank 映射 (1-based)
126
+ const kwSorted = [...keywordHits].sort((a, b) => b.score - a.score).slice(0, RRF_TOPN);
127
+ const semSorted = [...semanticHits].sort((a, b) => b.score - a.score).slice(0, RRF_TOPN);
175
128
  const kwRank = new Map();
176
129
  kwSorted.forEach((h, i) => kwRank.set(h.relPath, i + 1));
177
130
  const semRank = new Map();
178
131
  semSorted.forEach((h, i) => semRank.set(h.relPath, i + 1));
179
- // 收集所有唯一文件
180
- const allPaths = new Set([
181
- ...kwSorted.map(h => h.relPath),
182
- ...semSorted.map(h => h.relPath),
183
- ]);
184
- // 构建查找表
132
+ const allPaths = new Set([...kwSorted.map(h => h.relPath), ...semSorted.map(h => h.relPath)]);
185
133
  const kwMap = new Map(kwSorted.map(h => [h.relPath, h]));
186
134
  const semMap = new Map(semSorted.map(h => [h.relPath, h]));
187
- // RRF 缺省排名(未出现在某列表中的项用此值)
188
135
  const missingRank = RRF_K * 2;
189
136
  const merged = [];
190
137
  for (const relPath of allPaths) {
@@ -193,23 +140,16 @@ export async function hybridSearch(query) {
193
140
  const kwR = kwRank.get(relPath) ?? missingRank;
194
141
  const semR = semRank.get(relPath) ?? missingRank;
195
142
  const rrf = 1 / (RRF_K + kwR) + 1 / (RRF_K + semR);
196
- // 取最佳信息源构建结果
197
143
  const base = sem || kw;
198
- // 优先语义结果 snippet(含 LLM 编译内容),其次关键词 snippet
199
144
  let snippet = sem?.snippet || "";
200
- if (!snippet && kw?.snippet) {
145
+ if (!snippet && kw?.snippet)
201
146
  snippet = kw.snippet.replace(/\n/g, " | ");
202
- }
203
147
  merged.push({
204
- relPath: base.relPath,
205
- sourceDir: base.sourceDir,
206
- title: base.title,
207
- tags: base.tags,
208
- snippet,
148
+ relPath: base.relPath, sourceDir: base.sourceDir,
149
+ title: base.title, tags: base.tags, snippet,
209
150
  score: Math.round(rrf * 10000),
210
151
  semanticScore: sem?.semanticScore,
211
- chunkIndex: sem?.chunkIndex,
212
- chunkHeading: sem?.chunkHeading,
152
+ chunkIndex: sem?.chunkIndex, chunkHeading: sem?.chunkHeading,
213
153
  });
214
154
  }
215
155
  return merged.sort((a, b) => b.score - a.score);
@@ -0,0 +1 @@
1
+ {"version":3,"file":"semantic-search.js","sourceRoot":"","sources":["../../src/lib/semantic-search.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,25 @@
1
+ interface WikiConfig {
2
+ sources: string[];
3
+ semanticEnabled: boolean;
4
+ currentModelId: string;
5
+ lastScan: string;
6
+ }
7
+ export declare function readConfig(): WikiConfig;
8
+ export declare function writeConfig(c: WikiConfig): void;
9
+ export declare function getSources(): string[];
10
+ export declare function addSource(absPath: string): boolean;
11
+ /** 移除数据�?�?返回被移除的路径,未找到返回 null */
12
+ export declare function removeSource(target: string): string | null;
13
+ export declare function getLastScan(): string;
14
+ export declare function setLastScan(iso: string): void;
15
+ export declare function getSemanticEnabled(): boolean;
16
+ export declare function setSemanticEnabled(enabled: boolean): void;
17
+ export declare function readModelId(): string;
18
+ export declare function writeModelId(id: string): void;
19
+ export declare function getWikiModel(): string;
20
+ export declare function configStats(): {
21
+ sources: number;
22
+ lastScan: string;
23
+ };
24
+ export {};
25
+ //# sourceMappingURL=store-config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"store-config.d.ts","sourceRoot":"","sources":["../../src/lib/store-config.ts"],"names":[],"mappings":"AASA,UAAU,UAAU;IAClB,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,eAAe,EAAE,OAAO,CAAC;IACzB,cAAc,EAAE,MAAM,CAAC;IACvB,QAAQ,EAAE,MAAM,CAAC;CAClB;AAWD,wBAAgB,UAAU,IAAI,UAAU,CAMvC;AAED,wBAAgB,WAAW,CAAC,CAAC,EAAE,UAAU,GAAG,IAAI,CAE/C;AAID,wBAAgB,UAAU,IAAI,MAAM,EAAE,CAErC;AAED,wBAAgB,SAAS,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAMlD;AAED,kCAAkC;AAClC,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAU1D;AAID,wBAAgB,WAAW,IAAI,MAAM,CAEpC;AAED,wBAAgB,WAAW,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,CAI7C;AAID,wBAAgB,kBAAkB,IAAI,OAAO,CAE5C;AAED,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAIzD;AAID,wBAAgB,WAAW,IAAI,MAAM,CAEpC;AAED,wBAAgB,YAAY,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,CAI7C;AAID,wBAAgB,YAAY,IAAI,MAAM,CAErC;AAID,wBAAgB,WAAW,IAAI;IAC7B,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;CAClB,CAGA"}
@@ -0,0 +1,85 @@
1
+ // store-config.ts �?config.json 持久化层
2
+ //
3
+ // 管理: 数据源列�?/ 语义开�?/ 模型选择 / lastScan
4
+ // 不包含文件索引(已拆�?store-index.ts�?
5
+ import { existsSync, readFileSync, writeFileSync } from "node:fs";
6
+ import { configFile } from "../config.js";
7
+ const DEFAULT = {
8
+ sources: [],
9
+ semanticEnabled: false,
10
+ currentModelId: "bge-base-zh-v1.5",
11
+ lastScan: "",
12
+ };
13
+ // ---- 核心读写 ----
14
+ export function readConfig() {
15
+ try {
16
+ const p = configFile();
17
+ if (existsSync(p))
18
+ return { ...DEFAULT, ...JSON.parse(readFileSync(p, "utf-8")) };
19
+ }
20
+ catch { /* ignore */ }
21
+ return { ...DEFAULT };
22
+ }
23
+ export function writeConfig(c) {
24
+ writeFileSync(configFile(), JSON.stringify(c, null, 2), "utf-8");
25
+ }
26
+ // ---- 数据�?----
27
+ export function getSources() {
28
+ return readConfig().sources;
29
+ }
30
+ export function addSource(absPath) {
31
+ const c = readConfig();
32
+ if (c.sources.includes(absPath))
33
+ return false;
34
+ c.sources.push(absPath);
35
+ writeConfig(c);
36
+ return true;
37
+ }
38
+ /** 移除数据�?�?返回被移除的路径,未找到返回 null */
39
+ export function removeSource(target) {
40
+ const c = readConfig();
41
+ const idx = c.sources.findIndex((p) => p === target || p.endsWith(target));
42
+ if (idx < 0)
43
+ return null;
44
+ const removed = c.sources[idx];
45
+ c.sources.splice(idx, 1);
46
+ writeConfig(c);
47
+ return removed;
48
+ }
49
+ // ---- lastScan ----
50
+ export function getLastScan() {
51
+ return readConfig().lastScan;
52
+ }
53
+ export function setLastScan(iso) {
54
+ const c = readConfig();
55
+ c.lastScan = iso;
56
+ writeConfig(c);
57
+ }
58
+ // ---- 语义开�?----
59
+ export function getSemanticEnabled() {
60
+ return readConfig().semanticEnabled;
61
+ }
62
+ export function setSemanticEnabled(enabled) {
63
+ const c = readConfig();
64
+ c.semanticEnabled = enabled;
65
+ writeConfig(c);
66
+ }
67
+ // ---- 模型选择 ----
68
+ export function readModelId() {
69
+ return readConfig().currentModelId;
70
+ }
71
+ export function writeModelId(id) {
72
+ const c = readConfig();
73
+ c.currentModelId = id;
74
+ writeConfig(c);
75
+ }
76
+ // ---- wiki 对话模型 ----
77
+ export function getWikiModel() {
78
+ return "opencode-go/deepseek-v4-flash";
79
+ }
80
+ // ---- 统计 ----
81
+ export function configStats() {
82
+ const c = readConfig();
83
+ return { sources: c.sources.length, lastScan: c.lastScan };
84
+ }
85
+ //# sourceMappingURL=store-config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"store-config.js","sourceRoot":"","sources":["../../src/lib/store-config.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,14 @@
1
+ import type { FileEntry } from "./types.js";
2
+ export declare function readIndex(): Record<string, FileEntry>;
3
+ export declare function writeIndex(idx: Record<string, FileEntry>): void;
4
+ export declare function getIndex(): Record<string, FileEntry>;
5
+ export declare function getEntry(relPath: string): FileEntry | null;
6
+ export declare function mergeIndex(entries: FileEntry[]): void;
7
+ export declare function removeEntry(relPath: string): boolean;
8
+ export declare function updateEntryPath(oldRelPath: string, newRelPath: string, entry: FileEntry): boolean;
9
+ /** �?sourceDir 删除所有索引条�?*/
10
+ export declare function removeEntriesBySource(sourceDir: string): number;
11
+ export declare function indexStats(): {
12
+ files: number;
13
+ };
14
+ //# sourceMappingURL=store-index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"store-index.d.ts","sourceRoot":"","sources":["../../src/lib/store-index.ts"],"names":[],"mappings":"AAOA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAK5C,wBAAgB,SAAS,IAAI,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,CAMrD;AAED,wBAAgB,UAAU,CAAC,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,IAAI,CAE/D;AAID,wBAAgB,QAAQ,IAAI,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,CAEpD;AAED,wBAAgB,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,SAAS,GAAG,IAAI,CAE1D;AAID,wBAAgB,UAAU,CAAC,OAAO,EAAE,SAAS,EAAE,GAAG,IAAI,CAOrD;AAED,wBAAgB,WAAW,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAMpD;AAED,wBAAgB,eAAe,CAC7B,UAAU,EAAE,MAAM,EAClB,UAAU,EAAE,MAAM,EAClB,KAAK,EAAE,SAAS,GACf,OAAO,CAOT;AAED,2BAA2B;AAC3B,wBAAgB,qBAAqB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAW/D;AAID,wBAAgB,UAAU,IAAI;IAAE,KAAK,EAAE,MAAM,CAAA;CAAE,CAE9C"}
@@ -0,0 +1,72 @@
1
+ // store-index.ts �?index.json 持久化层
2
+ //
3
+ // 管理: 文件索引 Record<relPath, FileEntry>
4
+ // 拆自�?store-settings.ts,索引不再嵌�?config.json
5
+ import { existsSync, readFileSync, writeFileSync } from "node:fs";
6
+ import { indexFile } from "../config.js";
7
+ import { setLastScan } from "./store-config.js";
8
+ // ---- 核心读写 ----
9
+ export function readIndex() {
10
+ try {
11
+ const p = indexFile();
12
+ if (existsSync(p))
13
+ return JSON.parse(readFileSync(p, "utf-8"));
14
+ }
15
+ catch { /* ignore */ }
16
+ return {};
17
+ }
18
+ export function writeIndex(idx) {
19
+ writeFileSync(indexFile(), JSON.stringify(idx, null, 2), "utf-8");
20
+ }
21
+ // ---- 查询 ----
22
+ export function getIndex() {
23
+ return readIndex();
24
+ }
25
+ export function getEntry(relPath) {
26
+ return readIndex()[relPath] ?? null;
27
+ }
28
+ // ---- 修改 ----
29
+ export function mergeIndex(entries) {
30
+ const idx = readIndex();
31
+ for (const e of entries) {
32
+ idx[e.relPath] = e;
33
+ }
34
+ writeIndex(idx);
35
+ setLastScan(new Date().toISOString());
36
+ }
37
+ export function removeEntry(relPath) {
38
+ const idx = readIndex();
39
+ if (!idx[relPath])
40
+ return false;
41
+ delete idx[relPath];
42
+ writeIndex(idx);
43
+ return true;
44
+ }
45
+ export function updateEntryPath(oldRelPath, newRelPath, entry) {
46
+ const idx = readIndex();
47
+ if (!idx[oldRelPath])
48
+ return false;
49
+ delete idx[oldRelPath];
50
+ idx[newRelPath] = entry;
51
+ writeIndex(idx);
52
+ return true;
53
+ }
54
+ /** �?sourceDir 删除所有索引条�?*/
55
+ export function removeEntriesBySource(sourceDir) {
56
+ const idx = readIndex();
57
+ let count = 0;
58
+ for (const [key, entry] of Object.entries(idx)) {
59
+ if (entry.sourceDir === sourceDir) {
60
+ delete idx[key];
61
+ count++;
62
+ }
63
+ }
64
+ if (count)
65
+ writeIndex(idx);
66
+ return count;
67
+ }
68
+ // ---- 统计 ----
69
+ export function indexStats() {
70
+ return { files: Object.keys(readIndex()).length };
71
+ }
72
+ //# sourceMappingURL=store-index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"store-index.js","sourceRoot":"","sources":["../../src/lib/store-index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1 @@
1
+ {"version":3,"file":"store-vectors.d.ts","sourceRoot":"","sources":["../../src/lib/store-vectors.ts"],"names":[],"mappings":"AAUA,wBAAgB,aAAa,IAAI,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CASxD;AAED,wBAAgB,aAAa,CAC3B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,EACjC,KAAK,CAAC,EAAE,MAAM,EACd,GAAG,CAAC,EAAE,MAAM,GACX,IAAI,CAWN;AAID,wBAAgB,YAAY,IAAI,MAAM,CAAC,MAAM,EAAE,OAAO,YAAY,EAAE,SAAS,CAAC,CAO7E;AAED,wBAAgB,YAAY,CAC1B,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,YAAY,EAAE,SAAS,CAAC,GACxD,IAAI,CAUN;AAID,wBAAgB,eAAe,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAQrD;AAID,wBAAgB,iBAAiB,IAAI,MAAM,GAAG,SAAS,CAEtD;AAED,wBAAgB,eAAe,IAAI,MAAM,GAAG,SAAS,CAEpD;AAID,wBAAgB,YAAY,IAAI;IAAE,UAAU,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAA;CAAE,CAInF"}
@@ -1,14 +1,8 @@
1
- // store-vectors.ts vectors.json 持久化层
2
- // 管理: 语义向量 / chunk 元数据 / 模型维度信息
3
- //
4
- // 拆自 store.ts (P0-2), 仅负责 vectors.json 的读写。
5
- import { resolve } from "node:path";
1
+ // store-vectors.ts �?vectors.json 持久化层
2
+ // 管理: 语义向量 / chunk 元数�?/ 模型维度信息
3
+ // 适配�?extensions/wiki/lib/store-vectors.ts �?wikiHome 改为 config.ts
6
4
  import { existsSync, readFileSync, writeFileSync } from "node:fs";
7
- import { getWikiHome } from "./wiki-paths.js";
8
- function wikiHome() { return getWikiHome(); }
9
- function vectorFile() {
10
- return resolve(wikiHome(), "vectors.json");
11
- }
5
+ import { vectorFile } from "../config.js";
12
6
  // ---- 向量 ----
13
7
  export function getEmbeddings() {
14
8
  try {
@@ -70,7 +64,7 @@ export function removeEmbedding(relPath) {
70
64
  if (removed)
71
65
  setEmbeddings(emb);
72
66
  }
73
- // ---- 模型元信息 ----
67
+ // ---- 模型元信�?----
74
68
  export function getEmbeddingModel() {
75
69
  return readRaw()?.model;
76
70
  }
@@ -81,19 +75,14 @@ export function getEmbeddingDim() {
81
75
  export function vectorsStats() {
82
76
  const prev = readRaw();
83
77
  const emb = prev?.entries ?? {};
84
- return {
85
- embeddings: Object.keys(emb).length,
86
- model: prev?.model,
87
- dim: prev?.dim,
88
- };
78
+ return { embeddings: Object.keys(emb).length, model: prev?.model, dim: prev?.dim };
89
79
  }
90
80
  // ---- 内部 ----
91
81
  function readRaw() {
92
82
  try {
93
83
  const p = vectorFile();
94
- if (existsSync(p)) {
84
+ if (existsSync(p))
95
85
  return JSON.parse(readFileSync(p, "utf-8"));
96
- }
97
86
  }
98
87
  catch { /* ignore */ }
99
88
  return null;