@mastra/mongodb 1.12.1 → 1.13.0-alpha.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.
package/dist/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import { v4 } from '@lukeed/uuid';
2
2
  import { MastraError, ErrorCategory, ErrorDomain } from '@mastra/core/error';
3
- import { createVectorErrorId, AgentsStorage, TABLE_AGENTS, TABLE_AGENT_VERSIONS, createStorageErrorId, normalizePerPage, calculatePagination, BackgroundTasksStorage, TABLE_BACKGROUND_TASKS, BlobStore, TABLE_SKILL_BLOBS, DatasetsStorage, TABLE_DATASETS, TABLE_DATASET_ITEMS, TABLE_DATASET_VERSIONS, ensureDate, safelyParseJSON, TABLE_EXPERIMENTS, TABLE_EXPERIMENT_RESULTS, ExperimentsStorage, MCPClientsStorage, TABLE_MCP_CLIENTS, TABLE_MCP_CLIENT_VERSIONS, MCPServersStorage, TABLE_MCP_SERVERS, TABLE_MCP_SERVER_VERSIONS, MemoryStorage, TABLE_THREADS, TABLE_MESSAGES, TABLE_RESOURCES, NotificationsStorage, TABLE_NOTIFICATIONS, ObservabilityStorage, TABLE_SPANS, listTracesArgsSchema, toTraceSpans, PromptBlocksStorage, TABLE_PROMPT_BLOCKS, TABLE_PROMPT_BLOCK_VERSIONS, SchedulesStorage, TABLE_SCHEDULES, TABLE_SCHEDULE_TRIGGERS, ScorerDefinitionsStorage, TABLE_SCORER_DEFINITIONS, TABLE_SCORER_DEFINITION_VERSIONS, ScoresStorage, TABLE_SCORERS, SkillsStorage, TABLE_SKILLS, TABLE_SKILL_VERSIONS, WorkflowsStorage, TABLE_WORKFLOW_SNAPSHOT, WorkspacesStorage, TABLE_WORKSPACES, TABLE_WORKSPACE_VERSIONS, MastraCompositeStore, TraceStatus, parseDuration, normalizeScheduleTarget, transformScoreRow as transformScoreRow$1 } from '@mastra/core/storage';
3
+ import { createVectorErrorId, AgentsStorage, TABLE_AGENTS, TABLE_AGENT_VERSIONS, createStorageErrorId, normalizePerPage, calculatePagination, BackgroundTasksStorage, TABLE_BACKGROUND_TASKS, BlobStore, TABLE_SKILL_BLOBS, DatasetsStorage, TABLE_DATASETS, TABLE_DATASET_ITEMS, TABLE_DATASET_VERSIONS, ensureDate, safelyParseJSON, hasErrorCode, TABLE_EXPERIMENTS, TABLE_EXPERIMENT_RESULTS, ExperimentsStorage, MCPClientsStorage, TABLE_MCP_CLIENTS, TABLE_MCP_CLIENT_VERSIONS, MCPServersStorage, TABLE_MCP_SERVERS, TABLE_MCP_SERVER_VERSIONS, MemoryStorage, TABLE_THREADS, TABLE_MESSAGES, TABLE_RESOURCES, NotificationsStorage, TABLE_NOTIFICATIONS, ObservabilityStorage, TABLE_SPANS, listTracesArgsSchema, toTraceSpans, PromptBlocksStorage, TABLE_PROMPT_BLOCKS, TABLE_PROMPT_BLOCK_VERSIONS, SchedulesStorage, TABLE_SCHEDULES, TABLE_SCHEDULE_TRIGGERS, ScorerDefinitionsStorage, TABLE_SCORER_DEFINITIONS, TABLE_SCORER_DEFINITION_VERSIONS, ScoresStorage, TABLE_SCORERS, SkillsStorage, TABLE_SKILLS, TABLE_SKILL_VERSIONS, WorkflowsStorage, TABLE_WORKFLOW_SNAPSHOT, WorkspacesStorage, TABLE_WORKSPACES, TABLE_WORKSPACE_VERSIONS, MastraCompositeStore, TraceStatus, parseDuration, normalizeScheduleTarget, transformScoreRow as transformScoreRow$1 } from '@mastra/core/storage';
4
4
  import { MastraVector, validateUpsertInput, validateVectorValues } from '@mastra/core/vector';
5
5
  import { MongoClient, MongoBulkWriteError } from 'mongodb';
6
6
  import { BaseFilterTranslator } from '@mastra/core/vector/filter';
@@ -13,7 +13,7 @@ import { skillSnapshotFieldValuesEqual } from '@mastra/core/storage/domains/skil
13
13
 
14
14
  // package.json
15
15
  var package_default = {
16
- version: "1.12.1"};
16
+ version: "1.13.0-alpha.0"};
17
17
  var MongoDBFilterTranslator = class extends BaseFilterTranslator {
18
18
  getSupportedOperators() {
19
19
  return {
@@ -2216,6 +2216,11 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2216
2216
  keys: { datasetId: 1, datasetVersion: 1 },
2217
2217
  options: { name: "idx_dataset_items_datasetid_version" }
2218
2218
  },
2219
+ {
2220
+ collection: TABLE_DATASET_ITEMS,
2221
+ keys: { datasetId: 1, externalId: 1, datasetVersion: 1 },
2222
+ options: { name: "idx_dataset_items_datasetid_externalid_version", sparse: true }
2223
+ },
2219
2224
  {
2220
2225
  collection: TABLE_DATASET_ITEMS,
2221
2226
  keys: { datasetId: 1, validTo: 1, isDeleted: 1, createdAt: -1, id: 1 },
@@ -2286,6 +2291,7 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2286
2291
  id: row.id,
2287
2292
  datasetId: row.datasetId,
2288
2293
  datasetVersion: row.datasetVersion,
2294
+ externalId: row.externalId ?? null,
2289
2295
  organizationId: row.organizationId ?? null,
2290
2296
  projectId: row.projectId ?? null,
2291
2297
  input: typeof row.input === "string" ? safelyParseJSON(row.input) : row.input,
@@ -2317,7 +2323,8 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2317
2323
  // --- Dataset CRUD ---
2318
2324
  async createDataset(input) {
2319
2325
  try {
2320
- const id = randomUUID();
2326
+ const id = input.id ?? randomUUID();
2327
+ if (input.id !== void 0) this.validateCallerDefinedDatasetId(input.id);
2321
2328
  const now = /* @__PURE__ */ new Date();
2322
2329
  const collection = await this.getCollection(TABLE_DATASETS);
2323
2330
  const record = {
@@ -2342,6 +2349,10 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2342
2349
  await collection.insertOne(record);
2343
2350
  return this.transformDatasetRow(record);
2344
2351
  } catch (error) {
2352
+ if (input.id !== void 0 && hasErrorCode(error, /* @__PURE__ */ new Set([11e3]))) {
2353
+ const existing = await this.getDatasetById({ id: input.id });
2354
+ if (existing) return this.resolveExistingDataset(existing, { ...input, id: input.id });
2355
+ }
2345
2356
  if (error instanceof MastraError) throw error;
2346
2357
  throw new MastraError(
2347
2358
  {
@@ -2655,6 +2666,7 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2655
2666
  id: args.id,
2656
2667
  datasetId: args.datasetId,
2657
2668
  datasetVersion: newVersion,
2669
+ externalId: existing.externalId ?? null,
2658
2670
  organizationId: parentOrganizationId,
2659
2671
  projectId: parentProjectId,
2660
2672
  validTo: null,
@@ -2751,6 +2763,7 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2751
2763
  id,
2752
2764
  datasetId,
2753
2765
  datasetVersion: newVersion,
2766
+ externalId: existing.externalId ?? null,
2754
2767
  organizationId: parentOrganizationId,
2755
2768
  projectId: parentProjectId,
2756
2769
  validTo: null,
@@ -2792,37 +2805,27 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2792
2805
  // --- Batch operations ---
2793
2806
  async _doBatchInsertItems(input) {
2794
2807
  try {
2795
- const dataset = await this.getDatasetById({ id: input.datasetId });
2796
- if (!dataset) {
2808
+ if (input.items.length === 0) return [];
2809
+ const externalIds = [...new Set(input.items.flatMap((item) => item.externalId ? [item.externalId] : []))];
2810
+ if (externalIds.length > 0 && !await this.#connector.supportsTransactions()) {
2797
2811
  throw new MastraError({
2798
- id: createStorageErrorId("MONGODB", "BULK_ADD_ITEMS", "DATASET_NOT_FOUND"),
2812
+ id: "DATASET_ITEM_IDENTITY_REQUIRES_TRANSACTIONS",
2799
2813
  domain: ErrorDomain.STORAGE,
2800
2814
  category: ErrorCategory.USER,
2801
2815
  details: { datasetId: input.datasetId }
2802
2816
  });
2803
2817
  }
2804
- if (!input.items || input.items.length === 0) {
2805
- return [];
2806
- }
2807
- const now = /* @__PURE__ */ new Date();
2808
- const versionId = randomUUID();
2809
- const itemsWithIds = input.items.map((itemInput) => ({
2810
- generatedId: randomUUID(),
2811
- itemInput
2812
- }));
2813
2818
  const datasetsCollection = await this.getCollection(TABLE_DATASETS);
2814
2819
  const itemsCollection = await this.getCollection(TABLE_DATASET_ITEMS);
2815
2820
  const versionsCollection = await this.getCollection(TABLE_DATASET_VERSIONS);
2816
- let newVersion = 0;
2817
- let organizationId = null;
2818
- let projectId = null;
2821
+ let resolvedItems = [];
2819
2822
  await this.#connector.withTransaction(async (session) => {
2820
- const result = await datasetsCollection.findOneAndUpdate(
2823
+ const dataset = await datasetsCollection.findOneAndUpdate(
2821
2824
  { id: input.datasetId },
2822
- { $inc: { version: 1 } },
2825
+ { $inc: { identityRevision: 1 } },
2823
2826
  { session, returnDocument: "after" }
2824
2827
  );
2825
- if (!result) {
2828
+ if (!dataset) {
2826
2829
  throw new MastraError({
2827
2830
  id: createStorageErrorId("MONGODB", "BULK_ADD_ITEMS", "DATASET_NOT_FOUND"),
2828
2831
  domain: ErrorDomain.STORAGE,
@@ -2830,54 +2833,52 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2830
2833
  details: { datasetId: input.datasetId }
2831
2834
  });
2832
2835
  }
2833
- newVersion = result.version;
2834
- organizationId = result.organizationId ?? null;
2835
- projectId = result.projectId ?? null;
2836
- const docs = itemsWithIds.map(({ generatedId, itemInput }) => ({
2837
- id: generatedId,
2838
- datasetId: input.datasetId,
2839
- datasetVersion: newVersion,
2840
- organizationId,
2841
- projectId,
2842
- validTo: null,
2843
- isDeleted: false,
2844
- input: itemInput.input,
2845
- groundTruth: itemInput.groundTruth ?? null,
2846
- expectedTrajectory: itemInput.expectedTrajectory ?? null,
2847
- toolMocks: itemInput.toolMocks ?? null,
2848
- requestContext: itemInput.requestContext ?? null,
2849
- metadata: itemInput.metadata ?? null,
2850
- source: itemInput.source ?? null,
2851
- createdAt: now,
2852
- updatedAt: now
2853
- }));
2854
- await itemsCollection.insertMany(docs, { session });
2855
- await versionsCollection.insertOne(
2856
- {
2857
- id: versionId,
2858
- datasetId: input.datasetId,
2859
- version: newVersion,
2860
- createdAt: now
2861
- },
2862
- { session }
2836
+ const historyRows = externalIds.length === 0 ? [] : await itemsCollection.find({ datasetId: input.datasetId, externalId: { $in: externalIds } }, { session }).sort({ datasetVersion: 1 }).toArray();
2837
+ const plan = this.planDatasetItemBatch(
2838
+ input.items,
2839
+ historyRows.map((row) => this.transformItemRowFull(row)),
2840
+ randomUUID
2841
+ );
2842
+ const resolved = new Map(
2843
+ [...plan.existingCurrentItems].map(([id, row]) => [id, this.datasetItemFromRow(row)])
2863
2844
  );
2845
+ if (plan.inserts.length > 0) {
2846
+ const now = /* @__PURE__ */ new Date();
2847
+ const newVersion = Number(dataset.version) + 1;
2848
+ await datasetsCollection.updateOne(
2849
+ { id: input.datasetId },
2850
+ { $set: { version: newVersion, updatedAt: now } },
2851
+ { session }
2852
+ );
2853
+ for (const insert of plan.inserts) {
2854
+ const item = {
2855
+ id: insert.id,
2856
+ datasetId: input.datasetId,
2857
+ datasetVersion: newVersion,
2858
+ externalId: insert.item.externalId ?? null,
2859
+ organizationId: dataset.organizationId ?? null,
2860
+ projectId: dataset.projectId ?? null,
2861
+ input: insert.item.input,
2862
+ groundTruth: insert.item.groundTruth,
2863
+ expectedTrajectory: insert.item.expectedTrajectory,
2864
+ toolMocks: insert.item.toolMocks,
2865
+ requestContext: insert.item.requestContext,
2866
+ metadata: insert.item.metadata,
2867
+ source: insert.item.source,
2868
+ createdAt: now,
2869
+ updatedAt: now
2870
+ };
2871
+ await itemsCollection.insertOne({ ...item, validTo: null, isDeleted: false }, { session });
2872
+ resolved.set(item.id, item);
2873
+ }
2874
+ await versionsCollection.insertOne(
2875
+ { id: randomUUID(), datasetId: input.datasetId, version: newVersion, createdAt: now },
2876
+ { session }
2877
+ );
2878
+ }
2879
+ resolvedItems = plan.resolvedIds.map((id) => resolved.get(id));
2864
2880
  });
2865
- return itemsWithIds.map(({ generatedId, itemInput }) => ({
2866
- id: generatedId,
2867
- datasetId: input.datasetId,
2868
- datasetVersion: newVersion,
2869
- organizationId,
2870
- projectId,
2871
- input: itemInput.input,
2872
- groundTruth: itemInput.groundTruth,
2873
- expectedTrajectory: itemInput.expectedTrajectory,
2874
- toolMocks: itemInput.toolMocks,
2875
- requestContext: itemInput.requestContext,
2876
- metadata: itemInput.metadata,
2877
- source: itemInput.source,
2878
- createdAt: now,
2879
- updatedAt: now
2880
- }));
2881
+ return resolvedItems;
2881
2882
  } catch (error) {
2882
2883
  if (error instanceof MastraError) throw error;
2883
2884
  throw new MastraError(
@@ -2936,6 +2937,7 @@ var MongoDBDatasetsStorage = class extends DatasetsStorage {
2936
2937
  id: item.id,
2937
2938
  datasetId: input.datasetId,
2938
2939
  datasetVersion: newVersion,
2940
+ externalId: item.externalId ?? null,
2939
2941
  organizationId: parentOrganizationId,
2940
2942
  projectId: parentProjectId,
2941
2943
  validTo: null,