@mastra/convex 1.3.2 → 1.4.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 (44) hide show
  1. package/CHANGELOG.md +76 -0
  2. package/README.md +28 -17
  3. package/dist/{chunk-6P3LEDHY.cjs → chunk-2KILIA33.cjs} +315 -2
  4. package/dist/chunk-2KILIA33.cjs.map +1 -0
  5. package/dist/{chunk-77UWNT5X.js → chunk-MC2EQATP.js} +315 -2
  6. package/dist/chunk-MC2EQATP.js.map +1 -0
  7. package/dist/{chunk-MC75WADX.js → chunk-QWWFHN52.js} +41 -3
  8. package/dist/chunk-QWWFHN52.js.map +1 -0
  9. package/dist/{chunk-SFRHJGSM.cjs → chunk-ZCCKLZQH.cjs} +42 -2
  10. package/dist/chunk-ZCCKLZQH.cjs.map +1 -0
  11. package/dist/docs/SKILL.md +1 -1
  12. package/dist/docs/assets/SOURCE_MAP.json +41 -33
  13. package/dist/docs/references/reference-storage-convex.md +18 -11
  14. package/dist/index.cjs +586 -44
  15. package/dist/index.cjs.map +1 -1
  16. package/dist/index.js +542 -4
  17. package/dist/index.js.map +1 -1
  18. package/dist/schema.cjs +38 -30
  19. package/dist/schema.d.ts +95 -1
  20. package/dist/schema.d.ts.map +1 -1
  21. package/dist/schema.js +1 -1
  22. package/dist/server/index-map.d.ts.map +1 -1
  23. package/dist/server/index.cjs +41 -33
  24. package/dist/server/index.d.ts +1 -1
  25. package/dist/server/index.d.ts.map +1 -1
  26. package/dist/server/index.js +2 -2
  27. package/dist/server/observational-memory.d.ts +52 -0
  28. package/dist/server/observational-memory.d.ts.map +1 -0
  29. package/dist/server/storage.d.ts.map +1 -1
  30. package/dist/storage/db/index.d.ts +65 -14
  31. package/dist/storage/db/index.d.ts.map +1 -1
  32. package/dist/storage/domains/memory/index.d.ts +23 -1
  33. package/dist/storage/domains/memory/index.d.ts.map +1 -1
  34. package/dist/storage/domains/schedules/index.d.ts.map +1 -1
  35. package/dist/storage/domains/scores/index.d.ts.map +1 -1
  36. package/dist/storage/types.d.ts +133 -0
  37. package/dist/storage/types.d.ts.map +1 -1
  38. package/dist/vector/index.d.ts.map +1 -1
  39. package/dist/vector/native.d.ts.map +1 -1
  40. package/package.json +11 -11
  41. package/dist/chunk-6P3LEDHY.cjs.map +0 -1
  42. package/dist/chunk-77UWNT5X.js.map +0 -1
  43. package/dist/chunk-MC75WADX.js.map +0 -1
  44. package/dist/chunk-SFRHJGSM.cjs.map +0 -1
package/dist/index.js CHANGED
@@ -1,8 +1,7 @@
1
- export { mastraCache, mastraNativeVectorAction, mastraNativeVectorMutation, mastraNativeVectorQuery, mastraStorage } from './chunk-77UWNT5X.js';
2
- export { TABLE_BACKGROUND_TASKS, TABLE_CHANNEL_CONFIG, TABLE_CHANNEL_INSTALLATIONS, TABLE_MESSAGES, TABLE_RESOURCES, TABLE_SCHEDULES, TABLE_SCHEDULE_TRIGGERS, TABLE_SCORERS, TABLE_THREADS, TABLE_WORKFLOW_SNAPSHOT, defineMastraNativeVectorTable, mastraBackgroundTasksTable, mastraCacheListItemsTable, mastraCacheTable, mastraChannelConfigTable, mastraChannelInstallationsTable, mastraDocumentsTable, mastraMessagesTable, mastraResourcesTable, mastraScheduleTriggersTable, mastraSchedulesTable, mastraScoresTable, mastraThreadsTable, mastraVectorIndexesTable, mastraVectorsTable, mastraWorkflowSnapshotsTable } from './chunk-MC75WADX.js';
1
+ export { mastraCache, mastraNativeVectorAction, mastraNativeVectorMutation, mastraNativeVectorQuery, mastraStorage } from './chunk-MC2EQATP.js';
2
+ export { TABLE_BACKGROUND_TASKS, TABLE_CHANNEL_CONFIG, TABLE_CHANNEL_INSTALLATIONS, TABLE_MESSAGES, TABLE_OBSERVATIONAL_MEMORY, TABLE_RESOURCES, TABLE_SCHEDULES, TABLE_SCHEDULE_TRIGGERS, TABLE_SCORERS, TABLE_THREADS, TABLE_WORKFLOW_SNAPSHOT, defineMastraNativeVectorTable, mastraBackgroundTasksTable, mastraCacheListItemsTable, mastraCacheTable, mastraChannelConfigTable, mastraChannelInstallationsTable, mastraDocumentsTable, mastraMessagesTable, mastraObservationalMemoryTable, mastraResourcesTable, mastraScheduleTriggersTable, mastraSchedulesTable, mastraScoresTable, mastraThreadsTable, mastraVectorIndexesTable, mastraVectorsTable, mastraWorkflowSnapshotsTable } from './chunk-QWWFHN52.js';
3
3
  import { MastraServerCache } from '@mastra/core/cache';
4
4
  import { MastraCompositeStore, createVectorErrorId, MemoryStorage, TABLE_THREADS, TABLE_MESSAGES, TABLE_RESOURCES, createStorageErrorId, normalizePerPage, calculatePagination, filterByDateRange, safelyParseJSON, WorkflowsStorage, TABLE_WORKFLOW_SNAPSHOT, ScoresStorage, TABLE_SCORERS, ChannelsStorage, TABLE_CHANNEL_INSTALLATIONS, TABLE_CHANNEL_CONFIG, SchedulesStorage, TABLE_SCHEDULE_TRIGGERS, TABLE_SCHEDULES, BackgroundTasksStorage, TABLE_BACKGROUND_TASKS, normalizeScheduleTarget } from '@mastra/core/storage';
5
- import crypto from 'crypto';
6
5
  import { MastraBase } from '@mastra/core/base';
7
6
  import { MessageList } from '@mastra/core/agent';
8
7
  import { MastraError, ErrorCategory, ErrorDomain } from '@mastra/core/error';
@@ -275,6 +274,11 @@ var ConvexAdminClient = class {
275
274
  return result;
276
275
  }
277
276
  };
277
+
278
+ // src/storage/types.ts
279
+ var TABLE_OBSERVATIONAL_MEMORY2 = "mastra_observational_memory";
280
+
281
+ // src/storage/db/index.ts
278
282
  var LOAD_MANY_REQUEST_BATCH_SIZE = 10;
279
283
  function resolveConvexConfig(config) {
280
284
  if ("client" in config) {
@@ -331,7 +335,10 @@ var ConvexDB = class extends MastraBase {
331
335
  record: this.normalizeRecord(tableName, record)
332
336
  });
333
337
  }
334
- async batchInsert({ tableName, records }) {
338
+ async batchInsert({
339
+ tableName,
340
+ records
341
+ }) {
335
342
  if (records.length === 0) return;
336
343
  await this.client.callStorage({
337
344
  op: "batchInsert",
@@ -540,6 +547,67 @@ var ConvexDB = class extends MastraBase {
540
547
  hasMore = response.hasMore ?? false;
541
548
  }
542
549
  }
550
+ // ============================================
551
+ // Observational Memory Operations
552
+ // These always target TABLE_OBSERVATIONAL_MEMORY — the server rejects
553
+ // om* operations against any other table.
554
+ // ============================================
555
+ async omGetLatest(lookupKey) {
556
+ return this.client.callStorage({
557
+ op: "omGetLatest",
558
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
559
+ lookupKey
560
+ });
561
+ }
562
+ async omGetHistory(args) {
563
+ return this.client.callStorage({
564
+ op: "omGetHistory",
565
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
566
+ ...args
567
+ });
568
+ }
569
+ async omUpdateActive(args) {
570
+ await this.client.callStorage({
571
+ op: "omUpdateActive",
572
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
573
+ ...args
574
+ });
575
+ }
576
+ async omAppendBufferedChunk(args) {
577
+ await this.client.callStorage({
578
+ op: "omAppendBufferedChunk",
579
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
580
+ ...args
581
+ });
582
+ }
583
+ async omSwapBuffered(args) {
584
+ return this.client.callStorage({
585
+ op: "omSwapBuffered",
586
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
587
+ ...args
588
+ });
589
+ }
590
+ async omUpdateBufferedReflection(args) {
591
+ await this.client.callStorage({
592
+ op: "omUpdateBufferedReflection",
593
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
594
+ ...args
595
+ });
596
+ }
597
+ async omSwapBufferedReflection(args) {
598
+ return this.client.callStorage({
599
+ op: "omSwapBufferedReflection",
600
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
601
+ ...args
602
+ });
603
+ }
604
+ async omUpdateConfig(args) {
605
+ await this.client.callStorage({
606
+ op: "omUpdateConfig",
607
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
608
+ ...args
609
+ });
610
+ }
543
611
  normalizeRecord(tableName, record) {
544
612
  const normalized = { ...record };
545
613
  if (tableName === TABLE_WORKFLOW_SNAPSHOT && !normalized.id) {
@@ -901,7 +969,70 @@ function parseStoredResource(record) {
901
969
  updatedAt: new Date(record.updatedAt)
902
970
  };
903
971
  }
972
+ function toISO(value) {
973
+ return value instanceof Date ? value.toISOString() : value;
974
+ }
975
+ function serializeOMChunk(chunk) {
976
+ return {
977
+ ...chunk,
978
+ lastObservedAt: toISO(chunk.lastObservedAt),
979
+ createdAt: toISO(chunk.createdAt)
980
+ };
981
+ }
982
+ function parseOMChunk(chunk) {
983
+ return {
984
+ ...chunk,
985
+ lastObservedAt: new Date(chunk.lastObservedAt),
986
+ createdAt: new Date(chunk.createdAt)
987
+ };
988
+ }
989
+ function parseStoredOMChunks(value) {
990
+ if (!value) return void 0;
991
+ const parsed = safelyParseJSON(value);
992
+ if (!Array.isArray(parsed)) return void 0;
993
+ return parsed.map((chunk) => parseOMChunk(chunk));
994
+ }
995
+ function parseStoredOMRecord(doc) {
996
+ const config = safelyParseJSON(doc.config);
997
+ const metadata = doc.metadata ? safelyParseJSON(doc.metadata) : void 0;
998
+ return {
999
+ id: doc.id,
1000
+ scope: doc.scope,
1001
+ threadId: doc.threadId || null,
1002
+ resourceId: doc.resourceId,
1003
+ createdAt: new Date(doc.createdAt),
1004
+ updatedAt: new Date(doc.updatedAt),
1005
+ lastObservedAt: doc.lastObservedAt ? new Date(doc.lastObservedAt) : void 0,
1006
+ originType: doc.originType || "initial",
1007
+ generationCount: Number(doc.generationCount || 0),
1008
+ activeObservations: doc.activeObservations || "",
1009
+ bufferedObservationChunks: parseStoredOMChunks(doc.bufferedObservationChunks),
1010
+ // Deprecated fields (for backward compatibility)
1011
+ bufferedObservations: doc.activeObservationsPendingUpdate || void 0,
1012
+ bufferedObservationTokens: doc.bufferedObservationTokens ? Number(doc.bufferedObservationTokens) : void 0,
1013
+ bufferedMessageIds: void 0,
1014
+ // Use bufferedObservationChunks instead
1015
+ bufferedReflection: doc.bufferedReflection || void 0,
1016
+ bufferedReflectionTokens: doc.bufferedReflectionTokens ? Number(doc.bufferedReflectionTokens) : void 0,
1017
+ bufferedReflectionInputTokens: doc.bufferedReflectionInputTokens ? Number(doc.bufferedReflectionInputTokens) : void 0,
1018
+ reflectedObservationLineCount: doc.reflectedObservationLineCount ? Number(doc.reflectedObservationLineCount) : void 0,
1019
+ totalTokensObserved: Number(doc.totalTokensObserved || 0),
1020
+ observationTokenCount: Number(doc.observationTokenCount || 0),
1021
+ pendingMessageTokens: Number(doc.pendingMessageTokens || 0),
1022
+ isReflecting: Boolean(doc.isReflecting),
1023
+ isObserving: Boolean(doc.isObserving),
1024
+ isBufferingObservation: Boolean(doc.isBufferingObservation),
1025
+ isBufferingReflection: Boolean(doc.isBufferingReflection),
1026
+ lastBufferedAtTokens: Number(doc.lastBufferedAtTokens || 0),
1027
+ lastBufferedAtTime: doc.lastBufferedAtTime ? new Date(doc.lastBufferedAtTime) : null,
1028
+ config: config ?? {},
1029
+ metadata: metadata ?? void 0,
1030
+ observedMessageIds: doc.observedMessageIds || void 0,
1031
+ observedTimezone: doc.observedTimezone || void 0
1032
+ };
1033
+ }
904
1034
  var MemoryConvex = class extends MemoryStorage {
1035
+ supportsObservationalMemory = true;
905
1036
  #db;
906
1037
  constructor(config) {
907
1038
  super();
@@ -914,6 +1045,7 @@ var MemoryConvex = class extends MemoryStorage {
914
1045
  await this.#db.clearTable({ tableName: TABLE_THREADS });
915
1046
  await this.#db.clearTable({ tableName: TABLE_MESSAGES });
916
1047
  await this.#db.clearTable({ tableName: TABLE_RESOURCES });
1048
+ await this.#db.clearTable({ tableName: TABLE_OBSERVATIONAL_MEMORY2 });
917
1049
  }
918
1050
  async getThreadById({
919
1051
  threadId,
@@ -1107,6 +1239,51 @@ var MemoryConvex = class extends MemoryStorage {
1107
1239
  hasMore
1108
1240
  };
1109
1241
  }
1242
+ async listMessagesByResourceId(args) {
1243
+ const { resourceId, filter, perPage: perPageInput, page = 0, orderBy } = args;
1244
+ const { field, direction } = this.parseOrderBy(orderBy, "ASC");
1245
+ const perPage = normalizePerPage(perPageInput, 40);
1246
+ if (page < 0) {
1247
+ throw new MastraError(
1248
+ {
1249
+ id: createStorageErrorId("CONVEX", "LIST_MESSAGES_BY_RESOURCE_ID", "INVALID_PAGE"),
1250
+ domain: ErrorDomain.STORAGE,
1251
+ category: ErrorCategory.USER,
1252
+ details: { page }
1253
+ },
1254
+ new Error("page must be >= 0")
1255
+ );
1256
+ }
1257
+ const maxOffset = Number.MAX_SAFE_INTEGER / 2;
1258
+ if (page * perPage > maxOffset) {
1259
+ throw new MastraError(
1260
+ {
1261
+ id: createStorageErrorId("CONVEX", "LIST_MESSAGES_BY_RESOURCE_ID", "INVALID_PAGE"),
1262
+ domain: ErrorDomain.STORAGE,
1263
+ category: ErrorCategory.USER,
1264
+ details: { page, perPage }
1265
+ },
1266
+ new Error("page value too large")
1267
+ );
1268
+ }
1269
+ const { offset, perPage: perPageForResponse } = calculatePagination(page, perPageInput, perPage);
1270
+ let rows = await this.#db.queryTable(TABLE_MESSAGES, [{ field: "resourceId", value: resourceId }]);
1271
+ rows = filterByDateRange(rows, (row) => new Date(row.createdAt), filter?.dateRange);
1272
+ rows = this._sortStoredMessages(rows, field, direction);
1273
+ const total = rows.length;
1274
+ const paginatedRows = rows.slice(offset, offset + perPage);
1275
+ const list = new MessageList().add(
1276
+ paginatedRows.map((row) => this.parseStoredMessage(row)),
1277
+ "memory"
1278
+ );
1279
+ return {
1280
+ messages: list.get.all.db(),
1281
+ total,
1282
+ page,
1283
+ perPage: perPageForResponse,
1284
+ hasMore: offset + paginatedRows.length < total
1285
+ };
1286
+ }
1110
1287
  async listMessagesById({ messageIds }) {
1111
1288
  if (messageIds.length === 0) {
1112
1289
  return { messages: [] };
@@ -1246,6 +1423,16 @@ var MemoryConvex = class extends MemoryStorage {
1246
1423
  });
1247
1424
  return parseStoredResource(updated);
1248
1425
  }
1426
+ _sortStoredMessages(rows, field, direction) {
1427
+ return rows.sort((a, b) => {
1428
+ const aValue = field === "createdAt" || field === "updatedAt" ? new Date(a[field]).getTime() : a[field];
1429
+ const bValue = field === "createdAt" || field === "updatedAt" ? new Date(b[field]).getTime() : b[field];
1430
+ if (typeof aValue === "number" && typeof bValue === "number") {
1431
+ return direction === "ASC" ? aValue - bValue : bValue - aValue;
1432
+ }
1433
+ return direction === "ASC" ? String(aValue).localeCompare(String(bValue)) : String(bValue).localeCompare(String(aValue));
1434
+ });
1435
+ }
1249
1436
  _sortMessages(messages, field, direction) {
1250
1437
  return messages.sort((a, b) => {
1251
1438
  const aValue = field === "createdAt" || field === "updatedAt" ? new Date(a[field]).getTime() : a[field];
@@ -1352,6 +1539,357 @@ var MemoryConvex = class extends MemoryStorage {
1352
1539
  }
1353
1540
  }
1354
1541
  }
1542
+ // ============================================
1543
+ // Observational Memory Methods
1544
+ // ============================================
1545
+ getOMKey(threadId, resourceId) {
1546
+ return threadId ? `thread:${threadId}` : `resource:${resourceId}`;
1547
+ }
1548
+ omRecordNotFound(operation, id) {
1549
+ return new MastraError({
1550
+ id: createStorageErrorId("CONVEX", operation, "NOT_FOUND"),
1551
+ text: `Observational memory record not found: ${id}`,
1552
+ domain: ErrorDomain.STORAGE,
1553
+ category: ErrorCategory.THIRD_PARTY,
1554
+ details: { id }
1555
+ });
1556
+ }
1557
+ async getObservationalMemory(threadId, resourceId) {
1558
+ const lookupKey = this.getOMKey(threadId, resourceId);
1559
+ const doc = await this.#db.omGetLatest(lookupKey);
1560
+ return doc ? parseStoredOMRecord(doc) : null;
1561
+ }
1562
+ async getObservationalMemoryHistory(threadId, resourceId, limit = 10, options) {
1563
+ const lookupKey = this.getOMKey(threadId, resourceId);
1564
+ const docs = await this.#db.omGetHistory({
1565
+ lookupKey,
1566
+ limit,
1567
+ from: options?.from ? options.from.toISOString() : void 0,
1568
+ to: options?.to ? options.to.toISOString() : void 0,
1569
+ offset: options?.offset ?? void 0
1570
+ });
1571
+ return docs.map((doc) => parseStoredOMRecord(doc));
1572
+ }
1573
+ async initializeObservationalMemory(input) {
1574
+ const id = crypto.randomUUID();
1575
+ const now = /* @__PURE__ */ new Date();
1576
+ const lookupKey = this.getOMKey(input.threadId, input.resourceId);
1577
+ const record = {
1578
+ id,
1579
+ scope: input.scope,
1580
+ threadId: input.threadId,
1581
+ resourceId: input.resourceId,
1582
+ createdAt: now,
1583
+ updatedAt: now,
1584
+ // lastObservedAt starts undefined - all messages are "unobserved" initially
1585
+ lastObservedAt: void 0,
1586
+ originType: "initial",
1587
+ generationCount: 0,
1588
+ activeObservations: "",
1589
+ totalTokensObserved: 0,
1590
+ observationTokenCount: 0,
1591
+ pendingMessageTokens: 0,
1592
+ isReflecting: false,
1593
+ isObserving: false,
1594
+ isBufferingObservation: false,
1595
+ isBufferingReflection: false,
1596
+ lastBufferedAtTokens: 0,
1597
+ lastBufferedAtTime: null,
1598
+ config: input.config,
1599
+ observedTimezone: input.observedTimezone
1600
+ };
1601
+ await this.#db.insert({
1602
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1603
+ record: {
1604
+ id,
1605
+ lookupKey,
1606
+ scope: input.scope,
1607
+ resourceId: input.resourceId,
1608
+ threadId: input.threadId || null,
1609
+ activeObservations: "",
1610
+ activeObservationsPendingUpdate: null,
1611
+ originType: "initial",
1612
+ config: JSON.stringify(input.config ?? {}),
1613
+ generationCount: 0,
1614
+ lastObservedAt: null,
1615
+ lastReflectionAt: null,
1616
+ pendingMessageTokens: 0,
1617
+ totalTokensObserved: 0,
1618
+ observationTokenCount: 0,
1619
+ isObserving: false,
1620
+ isReflecting: false,
1621
+ isBufferingObservation: false,
1622
+ isBufferingReflection: false,
1623
+ lastBufferedAtTokens: 0,
1624
+ lastBufferedAtTime: null,
1625
+ observedTimezone: input.observedTimezone || null,
1626
+ createdAt: now.toISOString(),
1627
+ updatedAt: now.toISOString()
1628
+ }
1629
+ });
1630
+ return record;
1631
+ }
1632
+ async insertObservationalMemoryRecord(record) {
1633
+ const lookupKey = this.getOMKey(record.threadId, record.resourceId);
1634
+ await this.#db.insert({
1635
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1636
+ record: {
1637
+ id: record.id,
1638
+ lookupKey,
1639
+ scope: record.scope,
1640
+ resourceId: record.resourceId,
1641
+ threadId: record.threadId || null,
1642
+ activeObservations: record.activeObservations || "",
1643
+ activeObservationsPendingUpdate: null,
1644
+ originType: record.originType || "initial",
1645
+ config: JSON.stringify(record.config ?? {}),
1646
+ generationCount: record.generationCount || 0,
1647
+ lastObservedAt: record.lastObservedAt ? toISO(record.lastObservedAt) : null,
1648
+ lastReflectionAt: null,
1649
+ pendingMessageTokens: record.pendingMessageTokens || 0,
1650
+ totalTokensObserved: record.totalTokensObserved || 0,
1651
+ observationTokenCount: record.observationTokenCount || 0,
1652
+ observedMessageIds: record.observedMessageIds || null,
1653
+ bufferedObservationChunks: JSON.stringify(
1654
+ (Array.isArray(record.bufferedObservationChunks) ? record.bufferedObservationChunks : []).map(
1655
+ (chunk) => serializeOMChunk(chunk)
1656
+ )
1657
+ ),
1658
+ bufferedReflection: record.bufferedReflection || null,
1659
+ bufferedReflectionTokens: record.bufferedReflectionTokens ?? null,
1660
+ bufferedReflectionInputTokens: record.bufferedReflectionInputTokens ?? null,
1661
+ reflectedObservationLineCount: record.reflectedObservationLineCount ?? null,
1662
+ isObserving: record.isObserving || false,
1663
+ isReflecting: record.isReflecting || false,
1664
+ isBufferingObservation: record.isBufferingObservation || false,
1665
+ isBufferingReflection: record.isBufferingReflection || false,
1666
+ lastBufferedAtTokens: record.lastBufferedAtTokens || 0,
1667
+ lastBufferedAtTime: record.lastBufferedAtTime ? toISO(record.lastBufferedAtTime) : null,
1668
+ observedTimezone: record.observedTimezone || null,
1669
+ metadata: record.metadata ? JSON.stringify(record.metadata) : null,
1670
+ createdAt: toISO(record.createdAt),
1671
+ updatedAt: toISO(record.updatedAt)
1672
+ }
1673
+ });
1674
+ }
1675
+ async updateActiveObservations(input) {
1676
+ await this.#db.omUpdateActive({
1677
+ id: input.id,
1678
+ observations: input.observations,
1679
+ tokenCount: input.tokenCount,
1680
+ lastObservedAt: toISO(input.lastObservedAt),
1681
+ observedMessageIds: input.observedMessageIds ?? null,
1682
+ updatedAt: (/* @__PURE__ */ new Date()).toISOString()
1683
+ });
1684
+ }
1685
+ async updateBufferedObservations(input) {
1686
+ const chunk = {
1687
+ id: `ombuf-${crypto.randomUUID()}`,
1688
+ cycleId: input.chunk.cycleId,
1689
+ observations: input.chunk.observations,
1690
+ tokenCount: input.chunk.tokenCount,
1691
+ messageIds: input.chunk.messageIds,
1692
+ messageTokens: input.chunk.messageTokens,
1693
+ lastObservedAt: toISO(input.chunk.lastObservedAt),
1694
+ createdAt: (/* @__PURE__ */ new Date()).toISOString(),
1695
+ suggestedContinuation: input.chunk.suggestedContinuation,
1696
+ currentTask: input.chunk.currentTask,
1697
+ threadTitle: input.chunk.threadTitle,
1698
+ extractedValues: input.chunk.extractedValues,
1699
+ extractionFailures: input.chunk.extractionFailures
1700
+ };
1701
+ await this.#db.omAppendBufferedChunk({
1702
+ id: input.id,
1703
+ chunk,
1704
+ lastBufferedAtTime: input.lastBufferedAtTime ? toISO(input.lastBufferedAtTime) : void 0,
1705
+ updatedAt: (/* @__PURE__ */ new Date()).toISOString()
1706
+ });
1707
+ }
1708
+ async swapBufferedToActive(input) {
1709
+ return this.#db.omSwapBuffered({
1710
+ id: input.id,
1711
+ activationRatio: input.activationRatio,
1712
+ messageTokensThreshold: input.messageTokensThreshold,
1713
+ currentPendingTokens: input.currentPendingTokens,
1714
+ forceMaxActivation: input.forceMaxActivation,
1715
+ lastObservedAt: input.lastObservedAt ? toISO(input.lastObservedAt) : void 0,
1716
+ bufferedChunks: Array.isArray(input.bufferedChunks) ? input.bufferedChunks.map((chunk) => serializeOMChunk(chunk)) : void 0,
1717
+ now: (/* @__PURE__ */ new Date()).toISOString()
1718
+ });
1719
+ }
1720
+ async createReflectionGeneration(input) {
1721
+ const id = crypto.randomUUID();
1722
+ const now = /* @__PURE__ */ new Date();
1723
+ const lookupKey = this.getOMKey(input.currentRecord.threadId, input.currentRecord.resourceId);
1724
+ const record = {
1725
+ id,
1726
+ scope: input.currentRecord.scope,
1727
+ threadId: input.currentRecord.threadId,
1728
+ resourceId: input.currentRecord.resourceId,
1729
+ createdAt: now,
1730
+ updatedAt: now,
1731
+ lastObservedAt: input.currentRecord.lastObservedAt,
1732
+ originType: "reflection",
1733
+ generationCount: input.currentRecord.generationCount + 1,
1734
+ activeObservations: input.reflection,
1735
+ totalTokensObserved: input.currentRecord.totalTokensObserved,
1736
+ observationTokenCount: input.tokenCount,
1737
+ pendingMessageTokens: 0,
1738
+ isReflecting: false,
1739
+ isObserving: false,
1740
+ isBufferingObservation: false,
1741
+ isBufferingReflection: false,
1742
+ lastBufferedAtTokens: 0,
1743
+ lastBufferedAtTime: null,
1744
+ config: input.currentRecord.config,
1745
+ metadata: input.currentRecord.metadata,
1746
+ observedTimezone: input.currentRecord.observedTimezone
1747
+ };
1748
+ await this.#db.insert({
1749
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1750
+ record: {
1751
+ id,
1752
+ lookupKey,
1753
+ scope: record.scope,
1754
+ resourceId: record.resourceId,
1755
+ threadId: record.threadId || null,
1756
+ activeObservations: input.reflection,
1757
+ activeObservationsPendingUpdate: null,
1758
+ originType: "reflection",
1759
+ config: JSON.stringify(record.config ?? {}),
1760
+ generationCount: record.generationCount,
1761
+ lastObservedAt: record.lastObservedAt ? toISO(record.lastObservedAt) : null,
1762
+ lastReflectionAt: now.toISOString(),
1763
+ pendingMessageTokens: 0,
1764
+ totalTokensObserved: record.totalTokensObserved,
1765
+ observationTokenCount: record.observationTokenCount,
1766
+ isObserving: false,
1767
+ isReflecting: false,
1768
+ isBufferingObservation: false,
1769
+ isBufferingReflection: false,
1770
+ lastBufferedAtTokens: 0,
1771
+ lastBufferedAtTime: null,
1772
+ observedTimezone: record.observedTimezone || null,
1773
+ metadata: record.metadata ? JSON.stringify(record.metadata) : null,
1774
+ createdAt: now.toISOString(),
1775
+ updatedAt: now.toISOString()
1776
+ }
1777
+ });
1778
+ return record;
1779
+ }
1780
+ async updateBufferedReflection(input) {
1781
+ await this.#db.omUpdateBufferedReflection({
1782
+ id: input.id,
1783
+ reflection: input.reflection,
1784
+ tokenCount: input.tokenCount,
1785
+ inputTokenCount: input.inputTokenCount,
1786
+ reflectedObservationLineCount: input.reflectedObservationLineCount,
1787
+ updatedAt: (/* @__PURE__ */ new Date()).toISOString()
1788
+ });
1789
+ }
1790
+ async swapBufferedReflectionToActive(input) {
1791
+ const { currentRecord } = input;
1792
+ const serializedCurrentRecord = {
1793
+ id: currentRecord.id,
1794
+ lookupKey: this.getOMKey(currentRecord.threadId, currentRecord.resourceId),
1795
+ scope: currentRecord.scope,
1796
+ threadId: currentRecord.threadId || null,
1797
+ resourceId: currentRecord.resourceId,
1798
+ config: JSON.stringify(currentRecord.config ?? {}),
1799
+ metadata: currentRecord.metadata ? JSON.stringify(currentRecord.metadata) : null,
1800
+ observedTimezone: currentRecord.observedTimezone || null,
1801
+ lastObservedAt: currentRecord.lastObservedAt ? toISO(currentRecord.lastObservedAt) : null,
1802
+ totalTokensObserved: currentRecord.totalTokensObserved,
1803
+ generationCount: currentRecord.generationCount
1804
+ };
1805
+ const doc = await this.#db.omSwapBufferedReflection({
1806
+ currentRecord: serializedCurrentRecord,
1807
+ newId: crypto.randomUUID(),
1808
+ tokenCount: input.tokenCount,
1809
+ now: (/* @__PURE__ */ new Date()).toISOString()
1810
+ });
1811
+ return parseStoredOMRecord(doc);
1812
+ }
1813
+ async setReflectingFlag(id, isReflecting) {
1814
+ const found = await this.#db.patch({
1815
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1816
+ id,
1817
+ record: { isReflecting, updatedAt: /* @__PURE__ */ new Date() }
1818
+ });
1819
+ if (!found) {
1820
+ throw this.omRecordNotFound("SET_REFLECTING_FLAG", id);
1821
+ }
1822
+ }
1823
+ async setObservingFlag(id, isObserving) {
1824
+ const found = await this.#db.patch({
1825
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1826
+ id,
1827
+ record: { isObserving, updatedAt: /* @__PURE__ */ new Date() }
1828
+ });
1829
+ if (!found) {
1830
+ throw this.omRecordNotFound("SET_OBSERVING_FLAG", id);
1831
+ }
1832
+ }
1833
+ async setBufferingObservationFlag(id, isBuffering, lastBufferedAtTokens) {
1834
+ const found = await this.#db.patch({
1835
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1836
+ id,
1837
+ record: {
1838
+ isBufferingObservation: isBuffering,
1839
+ ...lastBufferedAtTokens !== void 0 ? { lastBufferedAtTokens } : {},
1840
+ updatedAt: /* @__PURE__ */ new Date()
1841
+ }
1842
+ });
1843
+ if (!found) {
1844
+ throw this.omRecordNotFound("SET_BUFFERING_OBSERVATION_FLAG", id);
1845
+ }
1846
+ }
1847
+ async setBufferingReflectionFlag(id, isBuffering) {
1848
+ const found = await this.#db.patch({
1849
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1850
+ id,
1851
+ record: { isBufferingReflection: isBuffering, updatedAt: /* @__PURE__ */ new Date() }
1852
+ });
1853
+ if (!found) {
1854
+ throw this.omRecordNotFound("SET_BUFFERING_REFLECTION_FLAG", id);
1855
+ }
1856
+ }
1857
+ async setPendingMessageTokens(id, tokenCount) {
1858
+ if (typeof tokenCount !== "number" || !Number.isFinite(tokenCount) || tokenCount < 0) {
1859
+ throw new MastraError({
1860
+ id: createStorageErrorId("CONVEX", "SET_PENDING_MESSAGE_TOKENS", "INVALID_INPUT"),
1861
+ text: `Invalid tokenCount: must be a finite non-negative number, got ${tokenCount}`,
1862
+ domain: ErrorDomain.STORAGE,
1863
+ category: ErrorCategory.USER,
1864
+ details: { id, tokenCount }
1865
+ });
1866
+ }
1867
+ const found = await this.#db.patch({
1868
+ tableName: TABLE_OBSERVATIONAL_MEMORY2,
1869
+ id,
1870
+ record: { pendingMessageTokens: tokenCount, updatedAt: /* @__PURE__ */ new Date() }
1871
+ });
1872
+ if (!found) {
1873
+ throw this.omRecordNotFound("SET_PENDING_MESSAGE_TOKENS", id);
1874
+ }
1875
+ }
1876
+ async clearObservationalMemory(threadId, resourceId) {
1877
+ const lookupKey = this.getOMKey(threadId, resourceId);
1878
+ const docs = await this.#db.queryTable(TABLE_OBSERVATIONAL_MEMORY2, [
1879
+ { field: "lookupKey", value: lookupKey }
1880
+ ]);
1881
+ await this.#db.deleteMany(
1882
+ TABLE_OBSERVATIONAL_MEMORY2,
1883
+ docs.map((doc) => doc.id)
1884
+ );
1885
+ }
1886
+ async updateObservationalMemoryConfig(input) {
1887
+ await this.#db.omUpdateConfig({
1888
+ id: input.id,
1889
+ config: JSON.stringify(input.config ?? {}),
1890
+ updatedAt: (/* @__PURE__ */ new Date()).toISOString()
1891
+ });
1892
+ }
1355
1893
  };
1356
1894
  var SCHEDULE_LIST_LIMIT = 8e3;
1357
1895
  function serializeJson2(value) {