memorix 1.1.8 → 1.1.9

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.js CHANGED
@@ -1787,6 +1787,7 @@ function loadYamlConfig(projectRoot) {
1787
1787
  agent: { ...userConfig.agent, ...projectConfig.agent },
1788
1788
  embedding: { ...userConfig.embedding, ...projectConfig.embedding },
1789
1789
  git: { ...userConfig.git, ...projectConfig.git },
1790
+ codegraph: { ...userConfig.codegraph, ...projectConfig.codegraph },
1790
1791
  behavior: { ...userConfig.behavior, ...projectConfig.behavior },
1791
1792
  server: { ...userConfig.server, ...projectConfig.server },
1792
1793
  team: { ...userConfig.team, ...projectConfig.team }
@@ -2069,6 +2070,7 @@ function mergeTomlConfig(base, override) {
2069
2070
  embedding: { ...base.embedding, ...override.embedding },
2070
2071
  hooks: { ...base.hooks, ...override.hooks },
2071
2072
  git: { ...base.git, ...override.git },
2073
+ codegraph: { ...base.codegraph, ...override.codegraph },
2072
2074
  server: { ...base.server, ...override.server }
2073
2075
  };
2074
2076
  }
@@ -2210,6 +2212,15 @@ var init_dotenv_loader = __esm({
2210
2212
  });
2211
2213
 
2212
2214
  // src/config/resolved-config.ts
2215
+ var resolved_config_exports = {};
2216
+ __export(resolved_config_exports, {
2217
+ getResolvedAgentLane: () => getResolvedAgentLane,
2218
+ getResolvedConfig: () => getResolvedConfig,
2219
+ getResolvedConfigForCwd: () => getResolvedConfigForCwd,
2220
+ getResolvedEmbeddingLane: () => getResolvedEmbeddingLane,
2221
+ getResolvedMemoryLane: () => getResolvedMemoryLane,
2222
+ resetResolvedConfigCache: () => resetResolvedConfigCache
2223
+ });
2213
2224
  import { homedir as homedir5 } from "os";
2214
2225
  import { existsSync as existsSync6 } from "fs";
2215
2226
  function getResolvedConfig(options = {}) {
@@ -2287,6 +2298,9 @@ function getResolvedConfig(options = {}) {
2287
2298
  excludePatterns: firstArray(toml.git?.exclude_patterns, yaml2.git?.excludePatterns),
2288
2299
  noiseKeywords: firstArray(toml.git?.noise_keywords, yaml2.git?.noiseKeywords)
2289
2300
  },
2301
+ codegraph: {
2302
+ excludePatterns: firstArray(toml.codegraph?.exclude_patterns, yaml2.codegraph?.excludePatterns)
2303
+ },
2290
2304
  server: {
2291
2305
  transport: first(toml.server?.transport, yaml2.server?.transport),
2292
2306
  dashboard: firstBool(toml.server?.dashboard, yaml2.server?.dashboard),
@@ -2308,6 +2322,10 @@ function getResolvedConfig(options = {}) {
2308
2322
  };
2309
2323
  return resolved;
2310
2324
  }
2325
+ function getResolvedConfigForCwd(cwd = process.cwd()) {
2326
+ const project = detectProject(cwd);
2327
+ return getResolvedConfig({ projectRoot: project?.rootPath ?? null });
2328
+ }
2311
2329
  function getResolvedAgentLane(options = {}) {
2312
2330
  const resolved = getResolvedConfig(options);
2313
2331
  return {
@@ -2324,6 +2342,8 @@ function getResolvedMemoryLane(options = {}) {
2324
2342
  function getResolvedEmbeddingLane(options = {}) {
2325
2343
  return getResolvedConfig(options).embedding;
2326
2344
  }
2345
+ function resetResolvedConfigCache() {
2346
+ }
2327
2347
  function first(...values) {
2328
2348
  return values.find((value) => value !== void 0 && value !== null && value !== "");
2329
2349
  }
@@ -4818,7 +4838,7 @@ __export(orama_store_exports, {
4818
4838
  resetDb: () => resetDb,
4819
4839
  searchObservations: () => searchObservations
4820
4840
  });
4821
- import { create, insert as insert2, search, remove as remove2, update, count } from "@orama/orama";
4841
+ import { create, insert as insert2, search, remove as remove2, update, count, getByID } from "@orama/orama";
4822
4842
  function getLastSearchMode(projectId) {
4823
4843
  return lastSearchModeByProject.get(projectId ?? SEARCH_MODE_DEFAULT_KEY) ?? "fulltext";
4824
4844
  }
@@ -4829,8 +4849,12 @@ function makeEntryKey(projectId, observationId) {
4829
4849
  return `${projectId ?? ""}::${observationId}`;
4830
4850
  }
4831
4851
  function rememberObservationDoc(doc) {
4832
- if (!doc.projectId || typeof doc.observationId !== "number") return;
4833
- docByObservationKey.set(makeEntryKey(doc.projectId, doc.observationId), doc);
4852
+ const publicDoc = { ...doc };
4853
+ delete publicDoc.embedding;
4854
+ if (doc.projectId && typeof doc.observationId === "number") {
4855
+ docByObservationKey.set(makeEntryKey(doc.projectId, doc.observationId), publicDoc);
4856
+ }
4857
+ return publicDoc;
4834
4858
  }
4835
4859
  function isCommandLikeQuery(query) {
4836
4860
  return COMMAND_LIKE_QUERY2.test(query);
@@ -4932,14 +4956,14 @@ async function batchGenerateEmbeddings(texts) {
4932
4956
  }
4933
4957
  async function hydrateIndex(observations2) {
4934
4958
  const database = await getDb();
4935
- const currentCount = await count(database);
4936
- if (currentCount > 0) return 0;
4937
4959
  let inserted = 0;
4938
4960
  for (const obs of observations2) {
4939
4961
  if (!obs || !obs.id || !obs.projectId) continue;
4940
4962
  try {
4963
+ const id = makeOramaObservationId(obs.projectId, obs.id);
4964
+ if (getByID(database, id)) continue;
4941
4965
  const doc = {
4942
- id: makeOramaObservationId(obs.projectId, obs.id),
4966
+ id,
4943
4967
  observationId: obs.id,
4944
4968
  entityName: obs.entityName || "",
4945
4969
  type: obs.type || "discovery",
@@ -5033,6 +5057,7 @@ async function searchObservations(options) {
5033
5057
  let searchParams = {
5034
5058
  term: originalQuery,
5035
5059
  limit: requestLimit,
5060
+ includeVectors: true,
5036
5061
  ...Object.keys(filters).length > 0 ? { where: filters } : {},
5037
5062
  // Search specific fields (not tokens, accessCount, etc.)
5038
5063
  properties: ["title", "entityName", "narrative", "facts", "concepts", "filesModified"],
@@ -5104,6 +5129,7 @@ async function searchObservations(options) {
5104
5129
  const vectorOnlyParams = {
5105
5130
  term: "",
5106
5131
  limit: requestLimit,
5132
+ includeVectors: true,
5107
5133
  ...Object.keys(filters).length > 0 ? { where: filters } : {},
5108
5134
  mode: "vector",
5109
5135
  vector: {
@@ -5402,6 +5428,7 @@ async function getObservationsByIds(ids, projectId) {
5402
5428
  }
5403
5429
  const searchResult = await search(database, {
5404
5430
  term: "",
5431
+ includeVectors: true,
5405
5432
  where: {
5406
5433
  observationId: { eq: id },
5407
5434
  ...projectId ? { projectId } : {}
@@ -5409,7 +5436,7 @@ async function getObservationsByIds(ids, projectId) {
5409
5436
  limit: 1
5410
5437
  });
5411
5438
  if (searchResult.hits.length > 0) {
5412
- results.push(searchResult.hits[0].document);
5439
+ results.push(rememberObservationDoc(searchResult.hits[0].document));
5413
5440
  }
5414
5441
  }
5415
5442
  return results;
@@ -9296,6 +9323,58 @@ var init_current_facts = __esm({
9296
9323
  }
9297
9324
  });
9298
9325
 
9326
+ // src/codegraph/exclude.ts
9327
+ function normalizeCodeGraphExcludePatterns(exclude) {
9328
+ return [.../* @__PURE__ */ new Set([
9329
+ ...DEFAULT_CODEGRAPH_EXCLUDES,
9330
+ ...(exclude ?? []).map((pattern) => pattern.trim()).filter(Boolean)
9331
+ ])];
9332
+ }
9333
+ function isCodeGraphExcludedPath(path20, exclude) {
9334
+ const normalized = normalizeCodePath2(path20);
9335
+ return normalizeCodeGraphExcludePatterns(exclude).some((pattern) => matchesPattern(normalized, normalizeCodePath2(pattern)));
9336
+ }
9337
+ function normalizeCodePath2(path20) {
9338
+ return path20.replace(/\\/g, "/").replace(/^\.\/+/, "");
9339
+ }
9340
+ function matchesPattern(path20, pattern) {
9341
+ if (pattern.endsWith("/**")) {
9342
+ const base = pattern.slice(0, -3);
9343
+ if (base.startsWith("**/")) {
9344
+ const suffix = base.slice(3);
9345
+ return path20 === suffix || path20.endsWith(`/${suffix}`) || path20.includes(`/${suffix}/`);
9346
+ }
9347
+ if (!base.includes("/")) {
9348
+ return path20 === base || path20.startsWith(`${base}/`) || path20.includes(`/${base}/`);
9349
+ }
9350
+ return path20 === base || path20.startsWith(`${base}/`);
9351
+ }
9352
+ if (pattern.startsWith("**/")) {
9353
+ const suffix = pattern.slice(3);
9354
+ return path20 === suffix || path20.endsWith(`/${suffix}`);
9355
+ }
9356
+ return path20 === pattern || path20.startsWith(`${pattern}/`);
9357
+ }
9358
+ var DEFAULT_CODEGRAPH_EXCLUDES;
9359
+ var init_exclude = __esm({
9360
+ "src/codegraph/exclude.ts"() {
9361
+ "use strict";
9362
+ init_esm_shims();
9363
+ DEFAULT_CODEGRAPH_EXCLUDES = [
9364
+ "node_modules/**",
9365
+ "dist/**",
9366
+ "build/**",
9367
+ "coverage/**",
9368
+ ".next/**",
9369
+ ".turbo/**",
9370
+ ".git/**",
9371
+ ".tmp/**",
9372
+ ".worktrees/**",
9373
+ ".claude/worktrees/**"
9374
+ ];
9375
+ }
9376
+ });
9377
+
9299
9378
  // src/codegraph/lite-provider.ts
9300
9379
  import { createHash as createHash5 } from "crypto";
9301
9380
  import { readdirSync as readdirSync3, readFileSync as readFileSync9, statSync as statSync2 } from "fs";
@@ -9311,18 +9390,6 @@ function languageForPath(path20) {
9311
9390
  const ext = extension(path20);
9312
9391
  return LANGUAGE_BY_EXTENSION.get(ext) ?? "unknown";
9313
9392
  }
9314
- function isExcluded(path20, exclude) {
9315
- const normalized = normalizeCodePath(path20);
9316
- return exclude.some((pattern) => {
9317
- const p = normalizeCodePath(pattern);
9318
- if (p.endsWith("/**")) {
9319
- const base = p.slice(0, -3);
9320
- return normalized === base || normalized.startsWith(`${base}/`);
9321
- }
9322
- if (p.startsWith("**/")) return normalized.endsWith(p.slice(3));
9323
- return normalized === p || normalized.startsWith(`${p}/`);
9324
- });
9325
- }
9326
9393
  function walk(root, exclude, maxFiles) {
9327
9394
  const out = [];
9328
9395
  const visit = (dir) => {
@@ -9336,7 +9403,7 @@ function walk(root, exclude, maxFiles) {
9336
9403
  for (const entry of entries) {
9337
9404
  const abs = join20(dir, entry.name);
9338
9405
  const rel = normalizeCodePath(relative(root, abs));
9339
- if (isExcluded(rel, exclude)) continue;
9406
+ if (isCodeGraphExcludedPath(rel, exclude)) continue;
9340
9407
  if (entry.isDirectory()) {
9341
9408
  if (entry.name === ".git" || entry.name === ".worktrees" || entry.name === ".tmp" || entry.name === "node_modules") continue;
9342
9409
  if (rel === ".claude/worktrees" || rel.startsWith(".claude/worktrees/")) continue;
@@ -9424,18 +9491,7 @@ function extractImportEdges(projectId, file, text, indexedAt) {
9424
9491
  return edges;
9425
9492
  }
9426
9493
  async function indexProjectLite(options) {
9427
- const exclude = options.exclude ?? [
9428
- "node_modules/**",
9429
- "dist/**",
9430
- "build/**",
9431
- "coverage/**",
9432
- ".next/**",
9433
- ".turbo/**",
9434
- ".git/**",
9435
- ".tmp/**",
9436
- ".worktrees/**",
9437
- ".claude/worktrees/**"
9438
- ];
9494
+ const exclude = normalizeCodeGraphExcludePatterns(options.exclude);
9439
9495
  const maxFiles = options.maxFiles ?? 5e3;
9440
9496
  const indexedAt = (/* @__PURE__ */ new Date()).toISOString();
9441
9497
  const paths = walk(options.projectRoot, exclude, maxFiles);
@@ -9474,6 +9530,7 @@ var init_lite_provider = __esm({
9474
9530
  "use strict";
9475
9531
  init_esm_shims();
9476
9532
  init_ids();
9533
+ init_exclude();
9477
9534
  LANGUAGE_BY_EXTENSION = /* @__PURE__ */ new Map([
9478
9535
  [".ts", "typescript"],
9479
9536
  [".tsx", "typescript"],
@@ -9643,24 +9700,17 @@ function countLanguages(files) {
9643
9700
  }
9644
9701
  return [...counts.entries()].map(([language, files2]) => ({ language, files: files2 })).sort((a, b) => a.language.localeCompare(b.language));
9645
9702
  }
9646
- function normalizePath2(path20) {
9647
- return path20.replace(/\\/g, "/");
9648
- }
9649
- function isGeneratedPath(path20) {
9650
- const normalized = normalizePath2(path20);
9651
- return /(^|\/)(dist|build|coverage|\.next|\.turbo|node_modules|\.git|\.tmp|\.worktrees)(\/|$)/i.test(normalized) || /(^|\/)\.claude\/worktrees(\/|$)/i.test(normalized);
9652
- }
9653
9703
  function suggestedReadRank(path20) {
9654
- const normalized = normalizePath2(path20);
9704
+ const normalized = path20.replace(/\\/g, "/");
9655
9705
  if (normalized.startsWith("src/")) return 0;
9656
9706
  if (normalized.startsWith("tests/") || normalized.startsWith("test/")) return 0;
9657
9707
  if (normalized.startsWith("packages/") && normalized.includes("/src/")) return 2;
9658
9708
  return 3;
9659
9709
  }
9660
- function compactSuggestedReads(paths, limit = 8) {
9661
- return uniq(paths).filter((path20) => !isGeneratedPath(path20)).sort((a, b) => suggestedReadRank(a) - suggestedReadRank(b)).slice(0, limit);
9710
+ function compactSuggestedReads(paths, limit = 8, exclude) {
9711
+ return uniq(paths).filter((path20) => !isCodeGraphExcludedPath(path20, exclude)).sort((a, b) => suggestedReadRank(a) - suggestedReadRank(b)).slice(0, limit);
9662
9712
  }
9663
- function collectGraph(store, projectId, observations2) {
9713
+ function collectGraph(store, projectId, observations2, exclude) {
9664
9714
  const files = store.listFiles(projectId);
9665
9715
  const symbols = files.flatMap((file) => store.listSymbolsForFile(file.id));
9666
9716
  const filesById = new Map(files.map((file) => [file.id, file]));
@@ -9682,7 +9732,9 @@ function collectGraph(store, projectId, observations2) {
9682
9732
  freshness[result.status] += 1;
9683
9733
  const observation = observationsById.get(ref.observationId);
9684
9734
  if (!observation) continue;
9685
- if (result.status === "current" && file) suggestedReads.push(file.path);
9735
+ const excluded = file ? isCodeGraphExcludedPath(file.path, exclude) : false;
9736
+ if (result.status === "current" && file && !excluded) suggestedReads.push(file.path);
9737
+ if (excluded) continue;
9686
9738
  sources.push({
9687
9739
  observationId: observation.id,
9688
9740
  title: observation.title,
@@ -9699,12 +9751,12 @@ function collectGraph(store, projectId, observations2) {
9699
9751
  refs,
9700
9752
  freshness,
9701
9753
  sources,
9702
- suggestedReads: compactSuggestedReads(suggestedReads)
9754
+ suggestedReads: compactSuggestedReads(suggestedReads, 8, exclude)
9703
9755
  };
9704
9756
  }
9705
9757
  function buildProjectContextOverview(input) {
9706
9758
  const active = activeObservations(input.observations, input.project.id);
9707
- const graph = collectGraph(input.store, input.project.id, active);
9759
+ const graph = collectGraph(input.store, input.project.id, active, input.exclude);
9708
9760
  const status = input.store.status(input.project.id);
9709
9761
  return {
9710
9762
  project: input.project,
@@ -9728,7 +9780,7 @@ function buildProjectContextOverview(input) {
9728
9780
  function buildProjectContextExplain(input) {
9729
9781
  const overview = buildProjectContextOverview(input);
9730
9782
  const active = activeObservations(input.observations, input.project.id);
9731
- const graph = collectGraph(input.store, input.project.id, active);
9783
+ const graph = collectGraph(input.store, input.project.id, active, input.exclude);
9732
9784
  return {
9733
9785
  project: input.project,
9734
9786
  sources: graph.sources.sort((a, b) => a.observationId - b.observationId || (a.path ?? "").localeCompare(b.path ?? "")),
@@ -9740,11 +9792,12 @@ var init_project_context = __esm({
9740
9792
  "use strict";
9741
9793
  init_esm_shims();
9742
9794
  init_freshness2();
9795
+ init_exclude();
9743
9796
  }
9744
9797
  });
9745
9798
 
9746
9799
  // src/codegraph/task-lens.ts
9747
- function normalizePath3(path20) {
9800
+ function normalizePath2(path20) {
9748
9801
  return path20.replace(/\\/g, "/");
9749
9802
  }
9750
9803
  function tokenize(text) {
@@ -9774,7 +9827,7 @@ function resolveTaskLens(task) {
9774
9827
  return best.score > 0 ? LENSES[best.id] : LENSES.general;
9775
9828
  }
9776
9829
  function pathKindScore(path20, lens) {
9777
- const normalized = normalizePath3(path20).toLowerCase();
9830
+ const normalized = normalizePath2(path20).toLowerCase();
9778
9831
  const name = normalized.split("/").pop() ?? normalized;
9779
9832
  const inDocs = normalized.startsWith("docs/") || name === "readme.md" || name.includes("readme");
9780
9833
  const isTest = /(^|\/)(tests?|__tests__|spec|fixtures?)\//.test(normalized) || /\.(test|spec)\.[cm]?[jt]sx?$/.test(normalized) || /\.(test|spec)\.py$/.test(normalized);
@@ -9823,7 +9876,7 @@ function sourceTaskMatchScore(source, task) {
9823
9876
  return 0;
9824
9877
  }
9825
9878
  function fallbackPathRank(path20) {
9826
- const normalized = normalizePath3(path20);
9879
+ const normalized = normalizePath2(path20);
9827
9880
  if (normalized.startsWith("src/")) return 0;
9828
9881
  if (normalized.startsWith("tests/") || normalized.startsWith("test/")) return 1;
9829
9882
  if (normalized.startsWith("packages/") && normalized.includes("/src/")) return 2;
@@ -9832,7 +9885,7 @@ function fallbackPathRank(path20) {
9832
9885
  }
9833
9886
  function rankLensPaths(paths, lens, task) {
9834
9887
  const tokens = tokenize(task ?? "");
9835
- return [...new Set(paths.map(normalizePath3))].map((path20, index) => ({
9888
+ return [...new Set(paths.map(normalizePath2))].map((path20, index) => ({
9836
9889
  path: path20,
9837
9890
  index,
9838
9891
  score: pathKindScore(path20, lens) + tokenScore(path20, tokens),
@@ -10086,6 +10139,7 @@ async function buildAutoProjectContext(input) {
10086
10139
  const now = input.now ?? /* @__PURE__ */ new Date();
10087
10140
  const task = input.task?.trim();
10088
10141
  const lens = resolveTaskLens(task);
10142
+ const exclude = input.exclude ?? getResolvedConfig({ projectRoot: input.project.rootPath }).codegraph.excludePatterns;
10089
10143
  const store = new CodeGraphStore();
10090
10144
  await store.init(input.dataDir);
10091
10145
  const initialStatus = store.status(input.project.id);
@@ -10103,7 +10157,8 @@ async function buildAutoProjectContext(input) {
10103
10157
  try {
10104
10158
  const indexed = await indexProjectLite({
10105
10159
  projectId: input.project.id,
10106
- projectRoot: input.project.rootPath
10160
+ projectRoot: input.project.rootPath,
10161
+ exclude
10107
10162
  });
10108
10163
  store.replaceProjectIndex(input.project.id, indexed);
10109
10164
  const backfill = await backfillMissingObservationCodeRefs(
@@ -10123,12 +10178,14 @@ async function buildAutoProjectContext(input) {
10123
10178
  const overview = buildProjectContextOverview({
10124
10179
  project: input.project,
10125
10180
  store,
10126
- observations: input.observations
10181
+ observations: input.observations,
10182
+ exclude
10127
10183
  });
10128
10184
  const explain = buildProjectContextExplain({
10129
10185
  project: input.project,
10130
10186
  store,
10131
- observations: input.observations
10187
+ observations: input.observations,
10188
+ exclude
10132
10189
  });
10133
10190
  return {
10134
10191
  project: input.project,
@@ -10338,6 +10395,7 @@ var init_auto_context = __esm({
10338
10395
  "src/codegraph/auto-context.ts"() {
10339
10396
  "use strict";
10340
10397
  init_esm_shims();
10398
+ init_resolved_config();
10341
10399
  init_binder();
10342
10400
  init_current_facts();
10343
10401
  init_lite_provider();
@@ -10365,10 +10423,6 @@ function tokenize2(text) {
10365
10423
  function timestampOf(observation) {
10366
10424
  return Date.parse(observation.updatedAt ?? observation.createdAt ?? "") || 0;
10367
10425
  }
10368
- function isGeneratedPath2(path20) {
10369
- const normalized = path20.replace(/\\/g, "/");
10370
- return /(^|\/)(dist|build|coverage|\.next|\.turbo|node_modules|\.git|\.tmp|\.worktrees)(\/|$)/i.test(normalized) || /(^|\/)\.claude\/worktrees(\/|$)/i.test(normalized);
10371
- }
10372
10426
  function relevanceScore(observation, taskTokens) {
10373
10427
  if (taskTokens.length === 0) return 0;
10374
10428
  const title = observation.title.toLowerCase();
@@ -10419,7 +10473,8 @@ function assembleContextPackForTask(input) {
10419
10473
  refs,
10420
10474
  files,
10421
10475
  symbols,
10422
- suggestedVerification: input.suggestedVerification
10476
+ suggestedVerification: input.suggestedVerification,
10477
+ exclude: input.exclude
10423
10478
  });
10424
10479
  }
10425
10480
  function assembleContextPack(input) {
@@ -10438,6 +10493,7 @@ function assembleContextPack(input) {
10438
10493
  observationIdsWithRefs.add(ref.observationId);
10439
10494
  const file = ref.fileId ? files.get(ref.fileId) : void 0;
10440
10495
  const symbol = ref.symbolId ? symbols.get(ref.symbolId) : void 0;
10496
+ if (file && isCodeGraphExcludedPath(file.path, input.exclude)) continue;
10441
10497
  const freshness = evaluateCodeRefFreshness(ref, file, symbol);
10442
10498
  if (freshness.status === "current") {
10443
10499
  const memoryKey = `${observation.id}:${freshness.status}`;
@@ -10503,8 +10559,8 @@ function buildContextPackPrompt(pack) {
10503
10559
  const reliableMemories = pack.memories.filter((memory) => memory.status === "current");
10504
10560
  const unboundMemories = pack.memories.filter((memory) => memory.status === "unbound");
10505
10561
  const lines = ["## Task", pack.task, "", "## Reliable Memories"];
10506
- const visibleCodeFacts = pack.codeFacts.filter((fact) => !isGeneratedPath2(fact.path)).slice(0, 5);
10507
- const visibleSuggestedReads = pack.suggestedReads.filter((path20) => !isGeneratedPath2(path20)).slice(0, 5);
10562
+ const visibleCodeFacts = pack.codeFacts.filter((fact) => !isCodeGraphExcludedPath(fact.path)).slice(0, 5);
10563
+ const visibleSuggestedReads = pack.suggestedReads.filter((path20) => !isCodeGraphExcludedPath(path20)).slice(0, 5);
10508
10564
  if (reliableMemories.length === 0) lines.push("- none");
10509
10565
  for (const memory of reliableMemories) {
10510
10566
  lines.push(`- #${memory.id} ${memory.status}: [${memory.type}] ${memory.title} (${memory.reason})`);
@@ -10539,6 +10595,7 @@ var init_context_pack = __esm({
10539
10595
  "use strict";
10540
10596
  init_esm_shims();
10541
10597
  init_freshness2();
10598
+ init_exclude();
10542
10599
  }
10543
10600
  });
10544
10601
 
@@ -20009,7 +20066,7 @@ The path should point to a directory containing a .git folder.`
20009
20066
  };
20010
20067
  const server = existingServer ?? new McpServer({
20011
20068
  name: "memorix",
20012
- version: true ? "1.1.8" : "1.0.1"
20069
+ version: true ? "1.1.9" : "1.0.1"
20013
20070
  });
20014
20071
  const originalRegisterTool = server.registerTool.bind(server);
20015
20072
  server.registerTool = ((name, ...args) => {
@@ -20711,15 +20768,18 @@ _Search mode: ${getLastSearchMode2(project.id)}_`;
20711
20768
  return withFreshIndex(async () => {
20712
20769
  const { CodeGraphStore: CodeGraphStore2 } = await Promise.resolve().then(() => (init_store(), store_exports));
20713
20770
  const { assembleContextPackForTask: assembleContextPackForTask2, buildContextPackPrompt: buildContextPackPrompt2 } = await Promise.resolve().then(() => (init_context_pack(), context_pack_exports));
20771
+ const { getResolvedConfig: getResolvedConfig2 } = await Promise.resolve().then(() => (init_resolved_config(), resolved_config_exports));
20714
20772
  const store = new CodeGraphStore2();
20715
20773
  await store.init(projectDir2);
20774
+ const exclude = getResolvedConfig2({ projectRoot: project.rootPath }).codegraph.excludePatterns;
20716
20775
  const observations2 = getAllObservations().filter((obs) => obs.projectId === project.id && (obs.status ?? "active") === "active").reverse();
20717
20776
  const pack = assembleContextPackForTask2({
20718
20777
  store,
20719
20778
  projectId: project.id,
20720
20779
  task,
20721
20780
  observations: observations2,
20722
- limit: typeof limit === "number" ? limit : 20
20781
+ limit: typeof limit === "number" ? limit : 20,
20782
+ exclude
20723
20783
  });
20724
20784
  const text = buildContextPackPrompt2(pack);
20725
20785
  return {