@anuma/sdk 1.1.0 → 1.1.2

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.
@@ -15,6 +15,7 @@ import {
15
15
  clearAllKeyPairs,
16
16
  clearEncryptionKey,
17
17
  clearKeyPair,
18
+ clearMemoryTopicsOverrideOp,
18
19
  clearMessagesOp,
19
20
  conversationToStoredRaw,
20
21
  convertUsageToStored,
@@ -106,6 +107,7 @@ import {
106
107
  searchChunksOp,
107
108
  searchMessagesOp,
108
109
  searchVaultMemories,
110
+ setMemoryEntitiesOp,
109
111
  shouldChunkMessage,
110
112
  stripToolCalls,
111
113
  updateConversationPinnedOp,
@@ -119,7 +121,7 @@ import {
119
121
  updateVaultMemoryEmbeddingOp,
120
122
  updateVaultMemoryOp,
121
123
  useEncryption
122
- } from "./chunk-Q2ANFWEP.mjs";
124
+ } from "./chunk-IMUF4U55.mjs";
123
125
  import {
124
126
  PiiRedactor,
125
127
  createStreamingDeAnonymizer,
@@ -4635,6 +4637,13 @@ function assembleMessagesWithHistory(historyMessages, callerMessages, summarySys
4635
4637
  ];
4636
4638
  }
4637
4639
 
4640
+ // src/lib/chat/imageParts.ts
4641
+ function isSendableImageURL(url) {
4642
+ if (!url) return false;
4643
+ const lower = url.toLowerCase();
4644
+ return lower.startsWith("http://") || lower.startsWith("https://") || lower.startsWith("data:image/");
4645
+ }
4646
+
4638
4647
  // src/lib/chat/sources.ts
4639
4648
  function extractSourcesFromToolCallEvents(toolCallEvents) {
4640
4649
  try {
@@ -6647,6 +6656,9 @@ __decorateClass([
6647
6656
  __decorateClass([
6648
6657
  field3("event_time_kind")
6649
6658
  ], VaultMemory.prototype, "eventTimeKind", 2);
6659
+ __decorateClass([
6660
+ field3("topics_user_managed")
6661
+ ], VaultMemory.prototype, "topicsUserManaged", 2);
6650
6662
  __decorateClass([
6651
6663
  readonly2,
6652
6664
  date3("created_at")
@@ -6658,6 +6670,9 @@ __decorateClass([
6658
6670
  field3("is_deleted")
6659
6671
  ], VaultMemory.prototype, "isDeleted", 2);
6660
6672
 
6673
+ // src/lib/memory/autoExtract.ts
6674
+ import { Q as Q4 } from "@nozbe/watermelondb";
6675
+
6661
6676
  // src/lib/memory/retain.ts
6662
6677
  var DEFAULT_AUTO_MERGE_THRESHOLD = 0.85;
6663
6678
  var DEFAULT_SCOPE = "private";
@@ -6705,12 +6720,15 @@ async function retain(content, ctx, options = {}) {
6705
6720
  preserveUpdatedAt: true,
6706
6721
  ...eventTimeUpdate && { eventTime: eventTimeUpdate }
6707
6722
  });
6708
- return {
6709
- action: "merge",
6710
- memoryId: targetId,
6711
- targetId,
6712
- proofCount: updated?.proofCount ?? (existing.proofCount ?? 1) + 1
6713
- };
6723
+ if (updated) {
6724
+ return {
6725
+ action: "merge",
6726
+ memoryId: targetId,
6727
+ targetId,
6728
+ proofCount: updated.proofCount ?? (existing.proofCount ?? 1) + 1
6729
+ };
6730
+ }
6731
+ await assertMergeTargetGoneOrThrow(ctx, targetId);
6714
6732
  }
6715
6733
  }
6716
6734
  }
@@ -6793,11 +6811,15 @@ async function tryConsolidate(trimmed, ctx, options) {
6793
6811
  preserveUpdatedAt: true,
6794
6812
  ...eventTimeUpdate && { eventTime: eventTimeUpdate }
6795
6813
  });
6814
+ if (!updated) {
6815
+ await assertMergeTargetGoneOrThrow(ctx, decision.targetId);
6816
+ return null;
6817
+ }
6796
6818
  return {
6797
6819
  action: "merge",
6798
6820
  memoryId: decision.targetId,
6799
6821
  targetId: decision.targetId,
6800
- proofCount: updated?.proofCount ?? (existing.proofCount ?? 1) + 1
6822
+ proofCount: updated.proofCount ?? (existing.proofCount ?? 1) + 1
6801
6823
  };
6802
6824
  }
6803
6825
  if (decision.action === "update" && decision.targetId && decision.content) {
@@ -6824,17 +6846,35 @@ async function tryConsolidate(trimmed, ctx, options) {
6824
6846
  preserveUpdatedAt: true,
6825
6847
  ...eventTimeUpdate && { eventTime: eventTimeUpdate }
6826
6848
  });
6849
+ if (!updated) {
6850
+ await assertMergeTargetGoneOrThrow(ctx, decision.targetId);
6851
+ return null;
6852
+ }
6827
6853
  return {
6828
6854
  action: "update",
6829
6855
  memoryId: decision.targetId,
6830
6856
  targetId: decision.targetId,
6831
- proofCount: updated?.proofCount ?? (existing.proofCount ?? 1) + 1
6857
+ proofCount: updated.proofCount ?? (existing.proofCount ?? 1) + 1
6832
6858
  };
6833
6859
  }
6834
6860
  return null;
6835
6861
  }
6862
+ async function assertMergeTargetGoneOrThrow(ctx, targetId) {
6863
+ const stillExists = await getVaultMemoryOp(ctx.vaultCtx, targetId);
6864
+ if (stillExists) {
6865
+ throw new Error(`retain: merge into memory ${targetId} failed to persist`);
6866
+ }
6867
+ }
6836
6868
 
6837
6869
  // src/lib/memory/autoExtract.ts
6870
+ async function isMemoryTopicsUserManaged(ctx, memoryId) {
6871
+ try {
6872
+ const rows = await ctx.database.get(VaultMemory.table).query(Q4.where("id", memoryId)).fetch();
6873
+ return rows[0]?.topicsUserManaged === true;
6874
+ } catch {
6875
+ return true;
6876
+ }
6877
+ }
6838
6878
  var DEFAULT_MODEL = "gpt-oss/gpt-oss-120b";
6839
6879
  var DEFAULT_MIN_CONFIDENCE = 0.7;
6840
6880
  var MAX_CONTENT_LENGTH = 200;
@@ -6993,7 +7033,9 @@ async function extractAndRetain(messages, retainCtx, options) {
6993
7033
  results.push(result);
6994
7034
  if (options.entityCtx && candidate.entities.length > 0) {
6995
7035
  try {
6996
- await linkMemoryEntitiesOp(options.entityCtx, result.memoryId, candidate.entities);
7036
+ if (!await isMemoryTopicsUserManaged(options.entityCtx, result.memoryId)) {
7037
+ await linkMemoryEntitiesOp(options.entityCtx, result.memoryId, candidate.entities);
7038
+ }
6997
7039
  } catch (err) {
6998
7040
  log.warn("[memory/extract] linkMemoryEntitiesOp failed", err);
6999
7041
  }
@@ -9914,7 +9956,7 @@ async function storedToLlmapiMessage(stored, encryptionKey, resolveMediaByIds) {
9914
9956
  const imageParts = [];
9915
9957
  if (stored.role !== "assistant" && stored.files?.length) {
9916
9958
  for (const file of stored.files) {
9917
- if (file.url) {
9959
+ if (isSendableImageURL(file.url)) {
9918
9960
  imageParts.push({
9919
9961
  type: "image_url",
9920
9962
  image_url: { url: file.url }
@@ -11849,7 +11891,7 @@ __decorateClass([
11849
11891
  ], VaultFolder.prototype, "context", 2);
11850
11892
 
11851
11893
  // src/lib/db/schema.ts
11852
- var SDK_SCHEMA_VERSION = 33;
11894
+ var SDK_SCHEMA_VERSION = 34;
11853
11895
  var sdkSchema = appSchema2({
11854
11896
  version: SDK_SCHEMA_VERSION,
11855
11897
  tables: [
@@ -11966,7 +12008,11 @@ var sdkSchema = appSchema2({
11966
12008
  // (start set, end null + kind='ongoing'), or none (both null).
11967
12009
  { name: "event_time_start", type: "number", isOptional: true, isIndexed: true },
11968
12010
  { name: "event_time_end", type: "number", isOptional: true },
11969
- { name: "event_time_kind", type: "string", isOptional: true }
12011
+ { name: "event_time_kind", type: "string", isOptional: true },
12012
+ // When true, the user has manually set this memory's topics (entity
12013
+ // links). Auto-extraction then leaves its links alone — the user owns
12014
+ // them. Null/false = topics are auto-derived (default).
12015
+ { name: "topics_user_managed", type: "boolean", isOptional: true }
11970
12016
  ]
11971
12017
  }),
11972
12018
  // Entity table — canonical names extracted from auto-extraction (W5).
@@ -12525,6 +12571,18 @@ var sdkMigrations = schemaMigrations2({
12525
12571
  columns: [{ name: "embedding_model", type: "string", isOptional: true }]
12526
12572
  })
12527
12573
  ]
12574
+ },
12575
+ // v33 -> v34: user-managed topics. `topics_user_managed` marks a memory
12576
+ // whose entity links the user has taken manual control of, so
12577
+ // auto-extraction stops touching them.
12578
+ {
12579
+ toVersion: 34,
12580
+ steps: [
12581
+ addColumns2({
12582
+ table: "memory_vault",
12583
+ columns: [{ name: "topics_user_managed", type: "boolean", isOptional: true }]
12584
+ })
12585
+ ]
12528
12586
  }
12529
12587
  ]
12530
12588
  });
@@ -12699,7 +12757,7 @@ function useDatabaseManager(walletAddress, manager) {
12699
12757
  }
12700
12758
 
12701
12759
  // src/lib/db/project/operations.ts
12702
- import { Q as Q4 } from "@nozbe/watermelondb";
12760
+ import { Q as Q5 } from "@nozbe/watermelondb";
12703
12761
 
12704
12762
  // src/lib/db/project/types.ts
12705
12763
  function generateProjectId() {
@@ -12730,15 +12788,15 @@ async function createProjectOp(ctx, opts, defaultName = "New Project") {
12730
12788
  return projectToStored(created);
12731
12789
  }
12732
12790
  async function getProjectOp(ctx, id) {
12733
- const results = await ctx.projectsCollection.query(Q4.where("project_id", id), Q4.where("is_deleted", false)).fetch();
12791
+ const results = await ctx.projectsCollection.query(Q5.where("project_id", id), Q5.where("is_deleted", false)).fetch();
12734
12792
  return results.length > 0 ? projectToStored(results[0]) : null;
12735
12793
  }
12736
12794
  async function getProjectsOp(ctx) {
12737
- const results = await ctx.projectsCollection.query(Q4.where("is_deleted", false), Q4.sortBy("created_at", Q4.desc)).fetch();
12795
+ const results = await ctx.projectsCollection.query(Q5.where("is_deleted", false), Q5.sortBy("created_at", Q5.desc)).fetch();
12738
12796
  return results.map(projectToStored);
12739
12797
  }
12740
12798
  async function updateProjectNameOp(ctx, id, name) {
12741
- const results = await ctx.projectsCollection.query(Q4.where("project_id", id), Q4.where("is_deleted", false)).fetch();
12799
+ const results = await ctx.projectsCollection.query(Q5.where("project_id", id), Q5.where("is_deleted", false)).fetch();
12742
12800
  if (results.length > 0) {
12743
12801
  await ctx.database.write(async () => {
12744
12802
  await results[0].update((proj) => {
@@ -12750,7 +12808,7 @@ async function updateProjectNameOp(ctx, id, name) {
12750
12808
  return false;
12751
12809
  }
12752
12810
  async function updateProjectOp(ctx, id, opts) {
12753
- const results = await ctx.projectsCollection.query(Q4.where("project_id", id), Q4.where("is_deleted", false)).fetch();
12811
+ const results = await ctx.projectsCollection.query(Q5.where("project_id", id), Q5.where("is_deleted", false)).fetch();
12754
12812
  if (results.length > 0) {
12755
12813
  await ctx.database.write(async () => {
12756
12814
  await results[0].update((proj) => {
@@ -12762,7 +12820,7 @@ async function updateProjectOp(ctx, id, opts) {
12762
12820
  return false;
12763
12821
  }
12764
12822
  async function deleteProjectOp(ctx, id) {
12765
- const results = await ctx.projectsCollection.query(Q4.where("project_id", id), Q4.where("is_deleted", false)).fetch();
12823
+ const results = await ctx.projectsCollection.query(Q5.where("project_id", id), Q5.where("is_deleted", false)).fetch();
12766
12824
  if (results.length > 0) {
12767
12825
  await ctx.database.write(async () => {
12768
12826
  await results[0].update((proj) => {
@@ -12775,18 +12833,18 @@ async function deleteProjectOp(ctx, id) {
12775
12833
  }
12776
12834
  async function getProjectConversationsOp(ctx, projectId) {
12777
12835
  const results = await ctx.conversationsCollection.query(
12778
- Q4.where("project_id", projectId),
12779
- Q4.where("is_deleted", false),
12780
- Q4.sortBy("created_at", Q4.desc)
12836
+ Q5.where("project_id", projectId),
12837
+ Q5.where("is_deleted", false),
12838
+ Q5.sortBy("created_at", Q5.desc)
12781
12839
  ).fetch();
12782
12840
  return results.map(conversationToStoredRaw);
12783
12841
  }
12784
12842
  async function getProjectConversationCountOp(ctx, projectId) {
12785
- return await ctx.conversationsCollection.query(Q4.where("project_id", projectId), Q4.where("is_deleted", false)).fetchCount();
12843
+ return await ctx.conversationsCollection.query(Q5.where("project_id", projectId), Q5.where("is_deleted", false)).fetchCount();
12786
12844
  }
12787
12845
 
12788
12846
  // src/react/useFiles.ts
12789
- import { Q as Q5 } from "@nozbe/watermelondb";
12847
+ import { Q as Q6 } from "@nozbe/watermelondb";
12790
12848
  import { useCallback as useCallback5, useEffect as useEffect4, useMemo as useMemo5, useState as useState5 } from "react";
12791
12849
  function useFiles(options) {
12792
12850
  const { database, walletAddress } = options;
@@ -12804,7 +12862,7 @@ function useFiles(options) {
12804
12862
  setIsLoading(true);
12805
12863
  try {
12806
12864
  const coll = database.get("media");
12807
- await coll.query(Q5.take(1)).fetch();
12865
+ await coll.query(Q6.take(1)).fetch();
12808
12866
  setMediaCollection(coll);
12809
12867
  setIsReady(true);
12810
12868
  } catch (error) {
@@ -13212,7 +13270,7 @@ function useFiles(options) {
13212
13270
  }
13213
13271
 
13214
13272
  // src/react/useProjects.ts
13215
- import { Q as Q6 } from "@nozbe/watermelondb";
13273
+ import { Q as Q7 } from "@nozbe/watermelondb";
13216
13274
  import { useCallback as useCallback6, useEffect as useEffect5, useMemo as useMemo6, useState as useState6 } from "react";
13217
13275
  function useProjects(options) {
13218
13276
  const { database, initialProjectId } = options;
@@ -13234,7 +13292,7 @@ function useProjects(options) {
13234
13292
  conversations: convColl?.table
13235
13293
  });
13236
13294
  getLogger().debug("[useProjects] Running test query on projects table...");
13237
- const testResult = await projColl.query(Q6.take(1)).fetch();
13295
+ const testResult = await projColl.query(Q7.take(1)).fetch();
13238
13296
  getLogger().debug(
13239
13297
  "[useProjects] Test query succeeded, found",
13240
13298
  testResult.length,
@@ -13321,7 +13379,7 @@ function useProjects(options) {
13321
13379
  if (!projectsCollection) {
13322
13380
  return;
13323
13381
  }
13324
- const subscription = projectsCollection.query(Q6.where("is_deleted", false)).observe().subscribe((records) => {
13382
+ const subscription = projectsCollection.query(Q7.where("is_deleted", false)).observe().subscribe((records) => {
13325
13383
  setProjects(records.map(projectToStored));
13326
13384
  });
13327
13385
  return () => subscription.unsubscribe();
@@ -13444,7 +13502,7 @@ function useProjects(options) {
13444
13502
  }
13445
13503
 
13446
13504
  // src/lib/db/settings/operations.ts
13447
- import { Q as Q7 } from "@nozbe/watermelondb";
13505
+ import { Q as Q8 } from "@nozbe/watermelondb";
13448
13506
  function modelPreferenceToStored(preference) {
13449
13507
  return {
13450
13508
  uniqueId: preference.id,
@@ -13453,12 +13511,12 @@ function modelPreferenceToStored(preference) {
13453
13511
  };
13454
13512
  }
13455
13513
  async function getModelPreferenceOp(ctx, walletAddress) {
13456
- const results = await ctx.modelPreferencesCollection.query(Q7.where("wallet_address", walletAddress)).fetch();
13514
+ const results = await ctx.modelPreferencesCollection.query(Q8.where("wallet_address", walletAddress)).fetch();
13457
13515
  return results.length > 0 ? modelPreferenceToStored(results[0]) : null;
13458
13516
  }
13459
13517
  async function setModelPreferenceOp(ctx, walletAddress, models) {
13460
13518
  const result = await ctx.database.write(async () => {
13461
- const results = await ctx.modelPreferencesCollection.query(Q7.where("wallet_address", walletAddress)).fetch();
13519
+ const results = await ctx.modelPreferencesCollection.query(Q8.where("wallet_address", walletAddress)).fetch();
13462
13520
  if (results.length > 0) {
13463
13521
  const preference = results[0];
13464
13522
  await preference.update((pref) => {
@@ -13476,7 +13534,7 @@ async function setModelPreferenceOp(ctx, walletAddress, models) {
13476
13534
  return modelPreferenceToStored(result);
13477
13535
  }
13478
13536
  async function deleteModelPreferenceOp(ctx, walletAddress) {
13479
- const results = await ctx.modelPreferencesCollection.query(Q7.where("wallet_address", walletAddress)).fetch();
13537
+ const results = await ctx.modelPreferencesCollection.query(Q8.where("wallet_address", walletAddress)).fetch();
13480
13538
  if (results.length === 0) return false;
13481
13539
  await ctx.database.write(async () => {
13482
13540
  await results[0].destroyPermanently();
@@ -13500,7 +13558,7 @@ var settingsStorageSchema = appSchema3({
13500
13558
  });
13501
13559
 
13502
13560
  // src/lib/db/vaultFolders/operations.ts
13503
- import { Q as Q8 } from "@nozbe/watermelondb";
13561
+ import { Q as Q9 } from "@nozbe/watermelondb";
13504
13562
  function folderToStored(folder) {
13505
13563
  return {
13506
13564
  uniqueId: folder.id,
@@ -13525,7 +13583,7 @@ async function createVaultFolderOp(ctx, opts) {
13525
13583
  return folderToStored(created);
13526
13584
  }
13527
13585
  async function getAllVaultFoldersOp(ctx) {
13528
- const results = await ctx.vaultFolderCollection.query(Q8.where("is_deleted", false), Q8.sortBy("created_at", Q8.desc)).fetch();
13586
+ const results = await ctx.vaultFolderCollection.query(Q9.where("is_deleted", false), Q9.sortBy("created_at", Q9.desc)).fetch();
13529
13587
  return results.map(folderToStored);
13530
13588
  }
13531
13589
  async function updateVaultFolderOp(ctx, id, opts) {
@@ -13542,7 +13600,7 @@ async function updateVaultFolderOp(ctx, id, opts) {
13542
13600
  })
13543
13601
  );
13544
13602
  if (scopeChanged) {
13545
- const memories = await ctx.vaultMemoryCollection.query(Q8.where("folder_id", id), Q8.where("is_deleted", false)).fetch();
13603
+ const memories = await ctx.vaultMemoryCollection.query(Q9.where("folder_id", id), Q9.where("is_deleted", false)).fetch();
13546
13604
  for (const memory of memories) {
13547
13605
  updates.push(
13548
13606
  memory.prepareUpdate((r) => {
@@ -13564,7 +13622,7 @@ async function deleteVaultFolderOp(ctx, id) {
13564
13622
  const record = await ctx.vaultFolderCollection.find(id);
13565
13623
  if (record.isDeleted) return false;
13566
13624
  await ctx.database.write(async () => {
13567
- const memories = await ctx.vaultMemoryCollection.query(Q8.where("folder_id", id), Q8.where("is_deleted", false)).fetch();
13625
+ const memories = await ctx.vaultMemoryCollection.query(Q9.where("folder_id", id), Q9.where("is_deleted", false)).fetch();
13568
13626
  const preparedMemories = memories.map(
13569
13627
  (memory) => memory.prepareUpdate((r) => {
13570
13628
  r._setRaw("folder_id", null);
@@ -13633,7 +13691,7 @@ async function updateVaultFolderContextOp(ctx, id, context) {
13633
13691
  }
13634
13692
  }
13635
13693
  async function getVaultFolderMemoryCountOp(ctx, folderId) {
13636
- return await ctx.vaultMemoryCollection.query(Q8.where("folder_id", folderId), Q8.where("is_deleted", false)).fetchCount();
13694
+ return await ctx.vaultMemoryCollection.query(Q9.where("folder_id", folderId), Q9.where("is_deleted", false)).fetchCount();
13637
13695
  }
13638
13696
 
13639
13697
  // src/lib/db/vaultFolders/defaults.ts
@@ -13679,7 +13737,7 @@ async function _ensureDefaultFoldersImpl(ctx) {
13679
13737
  import { useCallback as useCallback7, useMemo as useMemo7, useSyncExternalStore } from "react";
13680
13738
 
13681
13739
  // src/lib/db/userPreferences/operations.ts
13682
- import { Q as Q9 } from "@nozbe/watermelondb";
13740
+ import { Q as Q10 } from "@nozbe/watermelondb";
13683
13741
  function userPreferenceToStored(preference) {
13684
13742
  return {
13685
13743
  uniqueId: preference.id,
@@ -13694,7 +13752,7 @@ function userPreferenceToStored(preference) {
13694
13752
  };
13695
13753
  }
13696
13754
  async function getUserPreferenceOp(ctx, walletAddress) {
13697
- const results = await ctx.userPreferencesCollection.query(Q9.where("wallet_address", walletAddress)).fetch();
13755
+ const results = await ctx.userPreferencesCollection.query(Q10.where("wallet_address", walletAddress)).fetch();
13698
13756
  return results.length > 0 ? userPreferenceToStored(results[0]) : null;
13699
13757
  }
13700
13758
  async function createUserPreferenceOp(ctx, opts) {
@@ -13714,7 +13772,7 @@ async function createUserPreferenceOp(ctx, opts) {
13714
13772
  return userPreferenceToStored(created);
13715
13773
  }
13716
13774
  async function updateUserPreferenceOp(ctx, walletAddress, opts) {
13717
- const results = await ctx.userPreferencesCollection.query(Q9.where("wallet_address", walletAddress)).fetch();
13775
+ const results = await ctx.userPreferencesCollection.query(Q10.where("wallet_address", walletAddress)).fetch();
13718
13776
  if (results.length === 0) return null;
13719
13777
  const preference = results[0];
13720
13778
  await ctx.database.write(async () => {
@@ -13742,7 +13800,7 @@ async function updateUserPreferenceOp(ctx, walletAddress, opts) {
13742
13800
  async function setUserPreferenceOp(ctx, walletAddress, opts) {
13743
13801
  const now = Date.now();
13744
13802
  const result = await ctx.database.write(async () => {
13745
- const results = await ctx.userPreferencesCollection.query(Q9.where("wallet_address", walletAddress)).fetch();
13803
+ const results = await ctx.userPreferencesCollection.query(Q10.where("wallet_address", walletAddress)).fetch();
13746
13804
  if (results.length > 0) {
13747
13805
  const preference = results[0];
13748
13806
  await preference.update((pref) => {
@@ -13790,7 +13848,7 @@ async function updateModelsOp(ctx, walletAddress, models) {
13790
13848
  return updateUserPreferenceOp(ctx, walletAddress, { models });
13791
13849
  }
13792
13850
  async function deleteUserPreferenceOp(ctx, walletAddress) {
13793
- const results = await ctx.userPreferencesCollection.query(Q9.where("wallet_address", walletAddress)).fetch();
13851
+ const results = await ctx.userPreferencesCollection.query(Q10.where("wallet_address", walletAddress)).fetch();
13794
13852
  if (results.length === 0) return false;
13795
13853
  await ctx.database.write(async () => {
13796
13854
  await results[0].destroyPermanently();
@@ -13805,9 +13863,9 @@ async function migrateFromModelPreferencesOp(ctx, walletAddress) {
13805
13863
  if (existing) {
13806
13864
  return existing;
13807
13865
  }
13808
- const modelResults = await ctx.modelPreferencesCollection.query(Q9.where("wallet_address", walletAddress)).fetch();
13866
+ const modelResults = await ctx.modelPreferencesCollection.query(Q10.where("wallet_address", walletAddress)).fetch();
13809
13867
  const personalityKey = `${walletAddress}_personality_settings`;
13810
- const personalityResults = await ctx.modelPreferencesCollection.query(Q9.where("wallet_address", personalityKey)).fetch();
13868
+ const personalityResults = await ctx.modelPreferencesCollection.query(Q10.where("wallet_address", personalityKey)).fetch();
13811
13869
  if (modelResults.length === 0 && personalityResults.length === 0) {
13812
13870
  return null;
13813
13871
  }
@@ -13913,7 +13971,7 @@ var SLIDER_CONFIG = [
13913
13971
  ];
13914
13972
 
13915
13973
  // src/react/userSettingsStore.ts
13916
- import { Q as Q10 } from "@nozbe/watermelondb";
13974
+ import { Q as Q11 } from "@nozbe/watermelondb";
13917
13975
  var EMPTY_SNAPSHOT = Object.freeze({
13918
13976
  modelPreference: null,
13919
13977
  userPreference: null,
@@ -13975,7 +14033,7 @@ async function startLoad(entry, walletAddress) {
13975
14033
  }
13976
14034
  function startObserve(entry, walletAddress) {
13977
14035
  let isInitialEmission = true;
13978
- entry.observeSub = entry.storageCtx.userPreferencesCollection.query(Q10.where("wallet_address", walletAddress)).observeWithColumns([
14036
+ entry.observeSub = entry.storageCtx.userPreferencesCollection.query(Q11.where("wallet_address", walletAddress)).observeWithColumns([
13979
14037
  "nickname",
13980
14038
  "occupation",
13981
14039
  "description",
@@ -14229,7 +14287,7 @@ function useSettings(options) {
14229
14287
  }
14230
14288
 
14231
14289
  // src/lib/db/appFiles/operations.ts
14232
- import { Q as Q11 } from "@nozbe/watermelondb";
14290
+ import { Q as Q12 } from "@nozbe/watermelondb";
14233
14291
 
14234
14292
  // src/utils/paths.ts
14235
14293
  function normalizePath(p) {
@@ -14255,7 +14313,7 @@ async function putAppFileOp(ctx, conversationId, path, content) {
14255
14313
  const normalized = normalizePath(path);
14256
14314
  const now = Date.now();
14257
14315
  const result = await ctx.database.write(async () => {
14258
- const existing = await ctx.appFilesCollection.query(Q11.where("conversation_id", conversationId), Q11.where("path", normalized)).fetch();
14316
+ const existing = await ctx.appFilesCollection.query(Q12.where("conversation_id", conversationId), Q12.where("path", normalized)).fetch();
14259
14317
  if (existing.length > 0) {
14260
14318
  await existing[0].update((f) => {
14261
14319
  f._setRaw("content", content);
@@ -14275,11 +14333,11 @@ async function putAppFileOp(ctx, conversationId, path, content) {
14275
14333
  }
14276
14334
  async function getAppFileOp(ctx, conversationId, path) {
14277
14335
  const normalized = normalizePath(path);
14278
- const results = await ctx.appFilesCollection.query(Q11.where("conversation_id", conversationId), Q11.where("path", normalized)).fetch();
14336
+ const results = await ctx.appFilesCollection.query(Q12.where("conversation_id", conversationId), Q12.where("path", normalized)).fetch();
14279
14337
  return results.length > 0 ? appFileToStored(results[0]) : null;
14280
14338
  }
14281
14339
  async function getAppFilesOp(ctx, conversationId) {
14282
- const results = await ctx.appFilesCollection.query(Q11.where("conversation_id", conversationId)).fetch();
14340
+ const results = await ctx.appFilesCollection.query(Q12.where("conversation_id", conversationId)).fetch();
14283
14341
  return results.map(appFileToStored);
14284
14342
  }
14285
14343
  async function getAppFileMapOp(ctx, conversationId) {
@@ -14290,7 +14348,7 @@ async function getAppFileMapOp(ctx, conversationId) {
14290
14348
  }
14291
14349
  async function deleteAppFileOp(ctx, conversationId, path) {
14292
14350
  const normalized = normalizePath(path);
14293
- const results = await ctx.appFilesCollection.query(Q11.where("conversation_id", conversationId), Q11.where("path", normalized)).fetch();
14351
+ const results = await ctx.appFilesCollection.query(Q12.where("conversation_id", conversationId), Q12.where("path", normalized)).fetch();
14294
14352
  if (results.length === 0) return false;
14295
14353
  await ctx.database.write(async () => {
14296
14354
  await results[0].destroyPermanently();
@@ -14298,7 +14356,7 @@ async function deleteAppFileOp(ctx, conversationId, path) {
14298
14356
  return true;
14299
14357
  }
14300
14358
  async function deleteAllAppFilesOp(ctx, conversationId) {
14301
- const results = await ctx.appFilesCollection.query(Q11.where("conversation_id", conversationId)).fetch();
14359
+ const results = await ctx.appFilesCollection.query(Q12.where("conversation_id", conversationId)).fetch();
14302
14360
  if (results.length === 0) return;
14303
14361
  await ctx.database.write(async () => {
14304
14362
  const batch = results.map((file) => file.prepareDestroyPermanently());
@@ -14307,7 +14365,7 @@ async function deleteAllAppFilesOp(ctx, conversationId) {
14307
14365
  }
14308
14366
 
14309
14367
  // src/lib/db/savedTools/operations.ts
14310
- import { Q as Q12 } from "@nozbe/watermelondb";
14368
+ import { Q as Q13 } from "@nozbe/watermelondb";
14311
14369
  function savedToolToStored(tool) {
14312
14370
  return {
14313
14371
  uniqueId: tool.id,
@@ -14340,7 +14398,7 @@ async function createSavedToolOp(ctx, opts) {
14340
14398
  return savedToolToStored(created);
14341
14399
  }
14342
14400
  async function getAllSavedToolsOp(ctx) {
14343
- const results = await ctx.savedToolsCollection.query(Q12.where("is_deleted", false), Q12.sortBy("created_at", Q12.desc)).fetch();
14401
+ const results = await ctx.savedToolsCollection.query(Q13.where("is_deleted", false), Q13.sortBy("created_at", Q13.desc)).fetch();
14344
14402
  return results.map(savedToolToStored);
14345
14403
  }
14346
14404
  async function getSavedToolByIdOp(ctx, uniqueId) {
@@ -16863,9 +16921,9 @@ async function pushConversationToDropbox(database, conversationId, userAddress,
16863
16921
  const filename = `${conversationId}.json`;
16864
16922
  const existingFile = await findDropboxFile(token, filename, backupFolder);
16865
16923
  if (existingFile) {
16866
- const { Q: Q13 } = await import("@nozbe/watermelondb");
16924
+ const { Q: Q14 } = await import("@nozbe/watermelondb");
16867
16925
  const conversationsCollection = database.get("conversations");
16868
- const records = await conversationsCollection.query(Q13.where("conversation_id", conversationId)).fetch();
16926
+ const records = await conversationsCollection.query(Q14.where("conversation_id", conversationId)).fetch();
16869
16927
  if (records.length > 0) {
16870
16928
  const conversation = conversationToStoredRaw(records[0]);
16871
16929
  const localUpdated = conversation.updatedAt.getTime();
@@ -16903,9 +16961,9 @@ async function pushConversationToDropbox(database, conversationId, userAddress,
16903
16961
  }
16904
16962
  async function performDropboxExport(database, userAddress, token, deps, onProgress, backupFolder = DEFAULT_BACKUP_FOLDER) {
16905
16963
  await deps.requestEncryptionKey(userAddress);
16906
- const { Q: Q13 } = await import("@nozbe/watermelondb");
16964
+ const { Q: Q14 } = await import("@nozbe/watermelondb");
16907
16965
  const conversationsCollection = database.get("conversations");
16908
- const records = await conversationsCollection.query(Q13.where("is_deleted", false)).fetch();
16966
+ const records = await conversationsCollection.query(Q14.where("is_deleted", false)).fetch();
16909
16967
  const conversations = records.map(conversationToStoredRaw);
16910
16968
  const total = conversations.length;
16911
16969
  if (total === 0) {
@@ -17547,9 +17605,9 @@ async function pushConversationToDrive(database, conversationId, userAddress, to
17547
17605
  const filename = `${conversationId}.json`;
17548
17606
  const existingFile = await findDriveFile(activeToken, folderId, filename);
17549
17607
  if (existingFile) {
17550
- const { Q: Q13 } = await import("@nozbe/watermelondb");
17608
+ const { Q: Q14 } = await import("@nozbe/watermelondb");
17551
17609
  const conversationsCollection = database.get("conversations");
17552
- const records = await conversationsCollection.query(Q13.where("conversation_id", conversationId)).fetch();
17610
+ const records = await conversationsCollection.query(Q14.where("conversation_id", conversationId)).fetch();
17553
17611
  if (records.length > 0) {
17554
17612
  const conversation = conversationToStoredRaw(records[0]);
17555
17613
  const localUpdated = conversation.updatedAt.getTime();
@@ -17602,9 +17660,9 @@ async function performGoogleDriveExport(database, userAddress, token, deps, onPr
17602
17660
  return { success: false, uploaded: 0, skipped: 0, total: 0 };
17603
17661
  }
17604
17662
  const { token: activeToken } = folderResult;
17605
- const { Q: Q13 } = await import("@nozbe/watermelondb");
17663
+ const { Q: Q14 } = await import("@nozbe/watermelondb");
17606
17664
  const conversationsCollection = database.get("conversations");
17607
- const records = await conversationsCollection.query(Q13.where("is_deleted", false)).fetch();
17665
+ const records = await conversationsCollection.query(Q14.where("is_deleted", false)).fetch();
17608
17666
  const conversations = records.map(conversationToStoredRaw);
17609
17667
  const total = conversations.length;
17610
17668
  if (total === 0) {
@@ -18193,9 +18251,9 @@ async function pushConversationToICloud(database, conversationId, userAddress, d
18193
18251
  const filename = `${conversationId}.json`;
18194
18252
  const existingFile = await findICloudFile(filename);
18195
18253
  if (existingFile) {
18196
- const { Q: Q13 } = await import("@nozbe/watermelondb");
18254
+ const { Q: Q14 } = await import("@nozbe/watermelondb");
18197
18255
  const conversationsCollection = database.get("conversations");
18198
- const records = await conversationsCollection.query(Q13.where("conversation_id", conversationId)).fetch();
18256
+ const records = await conversationsCollection.query(Q14.where("conversation_id", conversationId)).fetch();
18199
18257
  if (records.length > 0) {
18200
18258
  const conversation = conversationToStoredRaw(records[0]);
18201
18259
  const localUpdated = conversation.updatedAt.getTime();
@@ -18225,9 +18283,9 @@ async function pushConversationToICloud(database, conversationId, userAddress, d
18225
18283
  }
18226
18284
  async function performICloudExport(database, userAddress, deps, onProgress) {
18227
18285
  await deps.requestEncryptionKey(userAddress);
18228
- const { Q: Q13 } = await import("@nozbe/watermelondb");
18286
+ const { Q: Q14 } = await import("@nozbe/watermelondb");
18229
18287
  const conversationsCollection = database.get("conversations");
18230
- const records = await conversationsCollection.query(Q13.where("is_deleted", false)).fetch();
18288
+ const records = await conversationsCollection.query(Q14.where("is_deleted", false)).fetch();
18231
18289
  const conversations = records.map(conversationToStoredRaw);
18232
18290
  const total = conversations.length;
18233
18291
  if (total === 0) {
@@ -22124,6 +22182,7 @@ export {
22124
22182
  clearICloudAuth,
22125
22183
  clearKeyPair,
22126
22184
  clearLazyTitleCache,
22185
+ clearMemoryTopicsOverrideOp,
22127
22186
  clearNotionToken,
22128
22187
  clearServerToolsCache,
22129
22188
  consoleLogger,
@@ -22334,6 +22393,7 @@ export {
22334
22393
  selectServerToolsForPrompt,
22335
22394
  serializeJsx,
22336
22395
  setLogger,
22396
+ setMemoryEntitiesOp,
22337
22397
  settingsStorageSchema,
22338
22398
  shouldChunkMessage,
22339
22399
  shouldRefreshTools,
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  recall
3
- } from "./chunk-Q2ANFWEP.mjs";
3
+ } from "./chunk-IMUF4U55.mjs";
4
4
  import "./chunk-DFVCS3QQ.mjs";
5
5
  import "./chunk-GYKJOWEO.mjs";
6
6
  export {
@@ -15983,6 +15983,7 @@ function vaultMemoryToStoredRaw(memory) {
15983
15983
  eventTimeStart: memory.eventTimeStart ?? null,
15984
15984
  eventTimeEnd: memory.eventTimeEnd ?? null,
15985
15985
  eventTimeKind: memory.eventTimeKind ?? null,
15986
+ topicsUserManaged: memory.topicsUserManaged ?? false,
15986
15987
  createdAt: memory.createdAt,
15987
15988
  updatedAt: memory.updatedAt,
15988
15989
  isDeleted: memory.isDeleted
@@ -16164,9 +16165,10 @@ function vaultMemoryRawToStoredRaw(raw) {
16164
16165
  eventTimeStart: raw.event_time_start ?? null,
16165
16166
  eventTimeEnd: raw.event_time_end ?? null,
16166
16167
  eventTimeKind: raw.event_time_kind ?? null,
16168
+ // SQLite stores booleans as 0/1, LokiJS as true/false — coerce both.
16169
+ topicsUserManaged: raw.topics_user_managed === true || raw.topics_user_managed === 1,
16167
16170
  createdAt: new Date(raw.created_at),
16168
16171
  updatedAt: new Date(raw.updated_at),
16169
- // SQLite stores booleans as 0/1, LokiJS as true/false — coerce both.
16170
16172
  isDeleted: raw.is_deleted === true || raw.is_deleted === 1
16171
16173
  };
16172
16174
  }
@@ -16250,6 +16252,9 @@ async function updateVaultMemoryOp(ctx, id, opts) {
16250
16252
  r._setRaw("event_time_end", opts.eventTime.end ?? null);
16251
16253
  r._setRaw("event_time_kind", opts.eventTime.kind ?? null);
16252
16254
  }
16255
+ if (opts.topicsUserManaged !== void 0) {
16256
+ r._setRaw("topics_user_managed", opts.topicsUserManaged);
16257
+ }
16253
16258
  if (opts.preserveUpdatedAt) {
16254
16259
  r._setRaw("updated_at", originalUpdatedAt);
16255
16260
  }
@@ -18816,7 +18821,7 @@ function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOp
18816
18821
  legacy.map((r) => ({ id: r.uniqueId, content: r.content, score: r.similarity }))
18817
18822
  );
18818
18823
  }
18819
- const { recall: recall2 } = await import("./recall-PFYFVYMS.mjs");
18824
+ const { recall: recall2 } = await import("./recall-LFYTTIIY.mjs");
18820
18825
  const result = await recall2(
18821
18826
  query,
18822
18827
  { vaultCtx, embeddingOptions, vaultCache: cache },