@ninjaxtools/slopdex 0.18.0 → 0.19.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.
@@ -1,13 +1,13 @@
1
1
  import {
2
2
  IndexDatabase
3
- } from "./chunk-6LHZCHEB.js";
3
+ } from "./chunk-GBEJHETS.js";
4
4
  import {
5
5
  OpenAIDescriptionProvider,
6
6
  isDescriptionProviderName
7
7
  } from "./chunk-TSURHRFF.js";
8
8
  import {
9
9
  analysisSimilarity
10
- } from "./chunk-KQRS5P4U.js";
10
+ } from "./chunk-5BO2LLXC.js";
11
11
  import {
12
12
  DEFAULT_PARALLELISM,
13
13
  assertPositiveInteger,
@@ -1012,8 +1012,10 @@ var CodeIndex = class {
1012
1012
  }
1013
1013
  /**
1014
1014
  * Whether a working-tree refresh changed nothing: same file set, same
1015
- * content, same language, still working-tree rows, no checkout to clear,
1016
- * and no recorded errors to retry. Skipping the write avoids a generation
1015
+ * content, same language, and still working-tree rows, with no checkout to
1016
+ * clear. Recorded indexing errors never force a refresh on their own; a
1017
+ * file with errors is retried only when its content changes or via an
1018
+ * explicit updateFiles upsert. Skipping the write avoids a generation
1017
1019
  * bump and, via foreign-key cascades, needlessly invalidating the
1018
1020
  * similarity cache for unchanged files. Description state must already be
1019
1021
  * quiescent: a refresh is what lazily clears stored descriptions after
@@ -1022,15 +1024,12 @@ var CodeIndex = class {
1022
1024
  */
1023
1025
  #isWorkingTreeClean(indexedFiles, prepared) {
1024
1026
  if (this.#database.getCheckpoint() !== null) return false;
1025
- if (this.#database.needsDiagnosticsScan()) return false;
1026
- if (this.#database.filesWithErrors().length > 0) return false;
1027
1027
  if (this.#database.descriptionsEnabled()) return false;
1028
1028
  if (indexedFiles.length !== prepared.length) return false;
1029
1029
  const status = this.status();
1030
1030
  if (status.descriptionCount > 0 || status.fileDescriptionCount > 0) return false;
1031
1031
  const indexedByPath = new Map(indexedFiles.map((file) => [file.path, file]));
1032
1032
  return prepared.every((file) => {
1033
- if (file.unavailable || file.errors.length > 0) return false;
1034
1033
  const indexed = indexedByPath.get(file.path);
1035
1034
  return !!indexed && indexed.sourceMode === "working-tree" && indexed.blobOid === file.blobOid && indexed.language === file.language && indexed.contentHash === file.contentHash;
1036
1035
  });
@@ -1045,8 +1044,7 @@ var CodeIndex = class {
1045
1044
  const overlayWorkingTree = target === head && options.includeWorkingTree !== false;
1046
1045
  const checkpoint = this.#database.getCheckpoint();
1047
1046
  const generation = this.#database.getGeneration();
1048
- const diagnosticsScan = this.#database.needsDiagnosticsScan();
1049
- const retryPaths = new Set(this.#database.filesWithErrors());
1047
+ const tooLargePaths = new Set(this.#database.filesWithFileTooLargeErrors());
1050
1048
  let reconcileAll = checkpoint === null;
1051
1049
  if (checkpoint && !await this.#git.isAncestor(checkpoint, target)) {
1052
1050
  if (!options.rebuildOnDivergence) throw new GitDivergenceError(checkpoint, target);
@@ -1084,7 +1082,7 @@ var CodeIndex = class {
1084
1082
  const claimedRenameSources = /* @__PURE__ */ new Set();
1085
1083
  for (const entry of eligibleEntries) {
1086
1084
  const indexed = indexedByPath.get(entry.path);
1087
- if (indexed?.sourceMode === "git" && indexed.blobOid === entry.oid && entry.size <= this.#maxFileSize && !diagnosticsScan && !retryPaths.has(entry.path)) continue;
1085
+ if (indexed?.sourceMode === "git" && indexed.blobOid === entry.oid && entry.size > this.#maxFileSize === tooLargePaths.has(entry.path)) continue;
1088
1086
  const matches = renameCandidates.filter((candidate) => candidate.blobOid === entry.oid && !claimedRenameSources.has(candidate.path));
1089
1087
  const previousPath = matches.length === 1 ? matches[0].path : void 0;
1090
1088
  if (previousPath) claimedRenameSources.add(previousPath);
@@ -1099,7 +1097,8 @@ var CodeIndex = class {
1099
1097
  for (const targetPath of eligibleTargetPaths) {
1100
1098
  const indexed = indexedByPath.get(targetPath);
1101
1099
  const entry = tree.get(targetPath);
1102
- if ((diagnosticsScan || retryPaths.has(targetPath) || entry.size > this.#maxFileSize || !indexed || indexed.sourceMode === "git" && indexed.blobOid !== entry.oid) && !upserts.has(targetPath)) {
1100
+ const sizeStateFlipped = indexed?.sourceMode === "git" && indexed.blobOid === entry.oid && entry.size > this.#maxFileSize !== tooLargePaths.has(targetPath);
1101
+ if ((!indexed || indexed.sourceMode === "git" && indexed.blobOid !== entry.oid || sizeStateFlipped) && !upserts.has(targetPath)) {
1103
1102
  upserts.set(targetPath, { entry });
1104
1103
  }
1105
1104
  }
@@ -1137,7 +1136,7 @@ var CodeIndex = class {
1137
1136
  }
1138
1137
  for (const [filePath, { entry, previousPath }] of upserts) {
1139
1138
  const indexed = indexedByPath.get(filePath);
1140
- if (!previousPath && indexed?.sourceMode === "git" && indexed.blobOid === entry.oid && entry.size <= this.#maxFileSize && !diagnosticsScan && !retryPaths.has(filePath)) upserts.delete(filePath);
1139
+ if (!previousPath && indexed?.sourceMode === "git" && indexed.blobOid === entry.oid && entry.size > this.#maxFileSize === tooLargePaths.has(filePath)) upserts.delete(filePath);
1141
1140
  }
1142
1141
  const workingPrepared = [];
1143
1142
  const workingDeletes = /* @__PURE__ */ new Set();
@@ -1224,7 +1223,7 @@ var CodeIndex = class {
1224
1223
  }
1225
1224
  }
1226
1225
  let embeddingsCreated = await this.#attachEmbeddings([...prepared, ...workingPrepared], options.signal);
1227
- const noChanges = !reconcileAll && !diagnosticsScan && checkpoint === target && prepared.length === 0 && deletes.size === 0 && workingPrepared.length === 0 && workingDeletes.size === 0;
1226
+ const noChanges = !reconcileAll && checkpoint === target && prepared.length === 0 && deletes.size === 0 && workingPrepared.length === 0 && workingDeletes.size === 0;
1228
1227
  while (true) {
1229
1228
  const resolvedAgain = await this.#git.resolveCommit(options.target ?? "HEAD");
1230
1229
  if (resolvedAgain !== target) throw new CodeIndexError("Target Git ref changed while indexing; retry the update.");
@@ -1877,26 +1876,30 @@ ${callable.description}` : null,
1877
1876
  }
1878
1877
  const functionsById = new Map(this.allFunctions().map((callable) => [callable.id, callable]));
1879
1878
  const lean = /* @__PURE__ */ new Map();
1879
+ let scanFloor = floor;
1880
+ for (const state of states.values()) scanFloor = Math.min(scanFloor, state.floor);
1880
1881
  for (const dirtyId of dirty) {
1881
1882
  throwIfAborted(options.signal);
1883
+ const prior = states.get(dirtyId);
1884
+ const keepWidth = Math.max(width, prior?.cachedWidth ?? width);
1882
1885
  const full = this.similarToFunction(dirtyId, {
1883
1886
  ...includeDescriptions ? { includeDescriptions: true } : {},
1884
1887
  limit: triples.length - 1,
1885
- minSimilarity: floor
1888
+ minSimilarity: scanFloor
1886
1889
  });
1887
1890
  const byTarget = /* @__PURE__ */ new Map();
1888
1891
  for (const match of full) byTarget.set(match.function.id, match);
1889
1892
  lean.set(dirtyId, byTarget);
1890
1893
  const triple = tripleById.get(dirtyId);
1891
- const top = full.slice(0, width);
1894
+ const top = full.slice(0, keepWidth);
1892
1895
  this.#database.storeSimilarityNeighbors(dirtyId, mode, top, {
1893
1896
  codeEmbeddingId: triple.codeEmbeddingId,
1894
1897
  descriptionEmbeddingId: triple.descriptionEmbeddingId,
1895
1898
  fileDescriptionEmbeddingId: triple.fileDescriptionEmbeddingId,
1896
- cachedWidth: width,
1899
+ cachedWidth: keepWidth,
1897
1900
  generation,
1898
- floor,
1899
- complete: full.length <= width
1901
+ floor: scanFloor,
1902
+ complete: full.length <= keepWidth
1900
1903
  });
1901
1904
  sourcesRefreshed += 1;
1902
1905
  pairsStored += top.length;
@@ -1906,32 +1909,33 @@ ${callable.description}` : null,
1906
1909
  for (const triple of triples) {
1907
1910
  throwIfAborted(options.signal);
1908
1911
  if (dirty.has(triple.functionId)) continue;
1912
+ const prior = states.get(triple.functionId);
1913
+ const keepFloor = Math.min(floor, prior?.floor ?? floor);
1914
+ const keepWidth = Math.max(width, prior?.cachedWidth ?? width);
1909
1915
  const cached = this.#database.cachedSimilarityNeighbors(triple.functionId, mode);
1910
- const kept = cached.filter((match) => match.similarity >= floor && !dirty.has(match.function.id) && functionsById.has(match.function.id));
1916
+ const kept = cached.filter((match) => match.similarity >= keepFloor && !dirty.has(match.function.id) && functionsById.has(match.function.id));
1911
1917
  const added = [];
1912
1918
  for (const [dirtyId, byTarget] of lean) {
1913
1919
  if (dirtyId === triple.functionId) continue;
1914
1920
  const match = byTarget.get(triple.functionId);
1915
1921
  const dirtyFunction = functionsById.get(dirtyId);
1916
- if (match && dirtyFunction) {
1922
+ if (match && match.similarity >= keepFloor && dirtyFunction) {
1917
1923
  const { function: _function, ...scores } = match;
1918
1924
  added.push({ ...scores, function: dirtyFunction });
1919
1925
  }
1920
1926
  }
1921
- const plusOne = [...kept, ...added].sort((left, right) => right.similarity - left.similarity || left.function.id - right.function.id).slice(0, width + 1);
1922
- const merged = plusOne.slice(0, width);
1923
- const contributorsComplete = triples.every((candidate) => dirty.has(candidate.functionId) || states.get(candidate.functionId)?.complete === true);
1924
- const complete = plusOne.length <= width && contributorsComplete;
1927
+ const plusOne = [...kept, ...added].sort((left, right) => right.similarity - left.similarity || left.function.id - right.function.id).slice(0, keepWidth + 1);
1928
+ const merged = plusOne.slice(0, keepWidth);
1929
+ const complete = plusOne.length <= keepWidth && (prior?.complete ?? false);
1925
1930
  const unchanged = merged.length === cached.length && merged.every((match, index) => match.function.id === cached[index].function.id && match.similarity === cached[index].similarity);
1926
1931
  if (unchanged) {
1927
- const narrowed = cached.some((match) => match.similarity < floor);
1928
1932
  this.#database.touchSimilarityCacheState(triple.functionId, mode, {
1929
1933
  codeEmbeddingId: triple.codeEmbeddingId,
1930
1934
  descriptionEmbeddingId: triple.descriptionEmbeddingId,
1931
1935
  fileDescriptionEmbeddingId: triple.fileDescriptionEmbeddingId,
1932
- cachedWidth: width,
1936
+ cachedWidth: keepWidth,
1933
1937
  generation,
1934
- floor: narrowed ? floor : states.get(triple.functionId)?.floor ?? floor,
1938
+ floor: keepFloor,
1935
1939
  storedCount: merged.length,
1936
1940
  complete
1937
1941
  });
@@ -1940,9 +1944,9 @@ ${callable.description}` : null,
1940
1944
  codeEmbeddingId: triple.codeEmbeddingId,
1941
1945
  descriptionEmbeddingId: triple.descriptionEmbeddingId,
1942
1946
  fileDescriptionEmbeddingId: triple.fileDescriptionEmbeddingId,
1943
- cachedWidth: width,
1947
+ cachedWidth: keepWidth,
1944
1948
  generation,
1945
- floor,
1949
+ floor: keepFloor,
1946
1950
  complete
1947
1951
  });
1948
1952
  pairsStored += merged.length;
@@ -2214,4 +2218,4 @@ function groupBy(values, keyFor) {
2214
2218
  export {
2215
2219
  CodeIndex
2216
2220
  };
2217
- //# sourceMappingURL=chunk-N6D66ASM.js.map
2221
+ //# sourceMappingURL=chunk-HMKVMRLF.js.map