@mastra/memory 1.25.0 → 1.26.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.
@@ -22,18 +22,19 @@ import { AsyncLocalStorage } from "async_hooks";
22
22
  import imageSize from "image-size";
23
23
  import { createTool } from "@mastra/core/tools";
24
24
  import { isStandardSchemaWithJSON as isStandardSchemaWithJSON$1, toStandardSchema as toStandardSchema$1 } from "@mastra/core/schema";
25
+ import { ErrorCategory, ErrorDomain, MastraError } from "@mastra/core/error";
25
26
  import { MessageHistory, MessageHistory as MessageHistory$1, SemanticRecall, WorkingMemory } from "@mastra/core/processors";
26
27
  import { inspect } from "util";
27
28
  import { structuredPatch } from "diff";
28
29
  //#region \0rolldown/runtime.js
29
- var __defProp$4 = Object.defineProperty;
30
+ var __defProp$3 = Object.defineProperty;
30
31
  var __exportAll = (all, no_symbols) => {
31
32
  let target = {};
32
- for (var name in all) __defProp$4(target, name, {
33
+ for (var name in all) __defProp$3(target, name, {
33
34
  get: all[name],
34
35
  enumerable: true
35
36
  });
36
- if (!no_symbols) __defProp$4(target, Symbol.toStringTag, { value: "Module" });
37
+ if (!no_symbols) __defProp$3(target, Symbol.toStringTag, { value: "Module" });
37
38
  return target;
38
39
  };
39
40
  //#endregion
@@ -179,9 +180,9 @@ Error message: ${getErrorMessage$4(cause)}`,
179
180
  _a13$5 = symbol13$5;
180
181
  var TypeValidationError$2 = _TypeValidationError;
181
182
  //#endregion
182
- //#region ../_vendored/ai_v4/dist/dist-e6zV1w-k.js
183
+ //#region ../_vendored/ai_v4/dist/index.js
183
184
  var __create = Object.create;
184
- var __defProp$3 = Object.defineProperty;
185
+ var __defProp$1$1 = Object.defineProperty;
185
186
  var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
186
187
  var __getOwnPropNames = Object.getOwnPropertyNames;
187
188
  var __getProtoOf = Object.getPrototypeOf;
@@ -190,14 +191,14 @@ var __commonJSMin = (cb, mod) => () => (mod || (cb((mod = { exports: {} }).expor
190
191
  var __copyProps = (to, from, except, desc) => {
191
192
  if (from && typeof from === "object" || typeof from === "function") for (var keys = __getOwnPropNames(from), i = 0, n = keys.length, key; i < n; i++) {
192
193
  key = keys[i];
193
- if (!__hasOwnProp.call(to, key) && key !== except) __defProp$3(to, key, {
194
+ if (!__hasOwnProp.call(to, key) && key !== except) __defProp$1$1(to, key, {
194
195
  get: ((k) => from[k]).bind(null, key),
195
196
  enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable
196
197
  });
197
198
  }
198
199
  return to;
199
200
  };
200
- var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule ? __defProp$3(target, "default", {
201
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule ? __defProp$1$1(target, "default", {
201
202
  value: mod,
202
203
  enumerable: true
203
204
  }) : target, mod));
@@ -411,8 +412,6 @@ function safeParseJSON$2({ text, schema }) {
411
412
  }
412
413
  }
413
414
  var { btoa: btoa$2, atob: atob$2 } = globalThis;
414
- //#endregion
415
- //#region ../_vendored/ai_v4/dist/index.js
416
415
  const ignoreOverride$2 = Symbol("Let zodToJsonSchema decide on which parser to use");
417
416
  const defaultOptions$2 = {
418
417
  name: void 0,
@@ -3714,7 +3713,7 @@ function trimStartOfStream() {
3714
3713
  };
3715
3714
  }
3716
3715
  //#endregion
3717
- //#region ../_vendored/ai_v5/dist/dist-Qv-F35RT.js
3716
+ //#region ../_vendored/ai_v5/dist/dist-BuEMdYEn.js
3718
3717
  var marker$1$4 = "vercel.ai.error";
3719
3718
  var symbol$1$3 = Symbol.for(marker$1$4);
3720
3719
  var _a$1$3;
@@ -4264,6 +4263,26 @@ async function cancelResponseBody$1(response) {
4264
4263
  await ((_a2 = response.body) == null ? void 0 : _a2.cancel());
4265
4264
  } catch (e) {}
4266
4265
  }
4266
+ var initialGlobalFetch$1 = globalThis.fetch;
4267
+ isNodeDefaultFetch$1(initialGlobalFetch$1);
4268
+ function isNodeDefaultFetch$1(fetch) {
4269
+ const source = Function.prototype.toString.call(fetch);
4270
+ return source.includes("internal/deps/undici") || source.includes("lazy loading of undici");
4271
+ }
4272
+ function getCurrentModulePath$1() {
4273
+ const originalPrepareStackTrace = Error.prepareStackTrace;
4274
+ try {
4275
+ Error.prepareStackTrace = (_error, callSites) => callSites;
4276
+ const error = /* @__PURE__ */ new Error("Capture current module path");
4277
+ Error.captureStackTrace(error, getCurrentModulePath$1);
4278
+ const [caller] = error.stack;
4279
+ const fileName = caller == null ? void 0 : caller.getFileName();
4280
+ if (fileName == null) throw new Error("Unable to determine the current module path");
4281
+ return fileName;
4282
+ } finally {
4283
+ Error.prepareStackTrace = originalPrepareStackTrace;
4284
+ }
4285
+ }
4267
4286
  var DEFAULT_MAX_DOWNLOAD_SIZE$1 = 2 * 1024 * 1024 * 1024;
4268
4287
  async function readResponseWithSizeLimit$1({ response, url, maxBytes = DEFAULT_MAX_DOWNLOAD_SIZE$1 }) {
4269
4288
  const contentLength = response.headers.get("content-length");
@@ -4373,11 +4392,11 @@ function withUserAgentSuffix$1(headers, ...userAgentSuffixParts) {
4373
4392
  normalizedHeaders.set("user-agent", [currentUserAgentHeader, ...userAgentSuffixParts].filter(Boolean).join(" "));
4374
4393
  return Object.fromEntries(normalizedHeaders.entries());
4375
4394
  }
4376
- var VERSION$4 = "3.0.30";
4395
+ var VERSION$4 = "3.0.31";
4377
4396
  var getOriginalFetch$1 = () => globalThis.fetch;
4378
- var getFromApi$1 = async ({ url, headers = {}, successfulResponseHandler, failedResponseHandler, abortSignal, fetch: fetch2 = getOriginalFetch$1() }) => {
4397
+ var getFromApi$1 = async ({ url, headers = {}, successfulResponseHandler, failedResponseHandler, abortSignal, fetch = getOriginalFetch$1() }) => {
4379
4398
  try {
4380
- const response = await fetch2(url, {
4399
+ const response = await fetch(url, {
4381
4400
  method: "GET",
4382
4401
  headers: withUserAgentSuffix$1(headers, `ai-sdk/provider-utils/${VERSION$4}`, getRuntimeEnvironmentUserAgent$1()),
4383
4402
  signal: abortSignal
@@ -4603,7 +4622,7 @@ function parseJsonEventStream$1({ stream, schema }) {
4603
4622
  } }));
4604
4623
  }
4605
4624
  var getOriginalFetch2$1 = () => globalThis.fetch;
4606
- var postJsonToApi$1 = async ({ url, headers, body, failedResponseHandler, successfulResponseHandler, abortSignal, fetch: fetch2 }) => postToApi$1({
4625
+ var postJsonToApi$1 = async ({ url, headers, body, failedResponseHandler, successfulResponseHandler, abortSignal, fetch }) => postToApi$1({
4607
4626
  url,
4608
4627
  headers: {
4609
4628
  "Content-Type": "application/json",
@@ -4616,11 +4635,11 @@ var postJsonToApi$1 = async ({ url, headers, body, failedResponseHandler, succes
4616
4635
  failedResponseHandler,
4617
4636
  successfulResponseHandler,
4618
4637
  abortSignal,
4619
- fetch: fetch2
4638
+ fetch
4620
4639
  });
4621
- var postToApi$1 = async ({ url, headers = {}, body, successfulResponseHandler, failedResponseHandler, abortSignal, fetch: fetch2 = getOriginalFetch2$1() }) => {
4640
+ var postToApi$1 = async ({ url, headers = {}, body, successfulResponseHandler, failedResponseHandler, abortSignal, fetch = getOriginalFetch2$1() }) => {
4622
4641
  try {
4623
- const response = await fetch2(url, {
4642
+ const response = await fetch(url, {
4624
4643
  method: "POST",
4625
4644
  headers: withUserAgentSuffix$1(headers, `ai-sdk/provider-utils/${VERSION$4}`, getRuntimeEnvironmentUserAgent$1()),
4626
4645
  body: body.content,
@@ -6682,7 +6701,7 @@ async function getVercelRequestId$1() {
6682
6701
  var _a10;
6683
6702
  return (_a10 = getContext$1().headers) == null ? void 0 : _a10["x-vercel-id"];
6684
6703
  }
6685
- var VERSION$2$2 = "2.0.115";
6704
+ var VERSION$2$2 = "2.0.125";
6686
6705
  var AI_GATEWAY_PROTOCOL_VERSION$1 = "0.0.1";
6687
6706
  function createGatewayProvider$1(options = {}) {
6688
6707
  var _a10, _b10;
@@ -7716,7 +7735,7 @@ function getGlobalProvider$1() {
7716
7735
  var _a16;
7717
7736
  return (_a16 = globalThis.AI_SDK_DEFAULT_PROVIDER) != null ? _a16 : gateway$1;
7718
7737
  }
7719
- var VERSION$5 = "5.0.216";
7738
+ var VERSION$5 = "5.0.226";
7720
7739
  var dataContentSchema$1 = z$1.union([
7721
7740
  z$1.string(),
7722
7741
  z$1.instanceof(Uint8Array),
@@ -8582,7 +8601,7 @@ var object$1 = ({ schema: inputSchema }) => {
8582
8601
  };
8583
8602
  };
8584
8603
  //#endregion
8585
- //#region ../_vendored/ai_v6/dist/dist-BomuqvJJ.js
8604
+ //#region ../_vendored/ai_v6/dist/dist-BTWHzT8H.js
8586
8605
  var marker$1 = "vercel.ai.error";
8587
8606
  var symbol$1$1 = Symbol.for(marker$1);
8588
8607
  var _a$1$1;
@@ -9153,6 +9172,26 @@ var DownloadError = class extends (_b$2 = AISDKError, _a$2 = symbol$2, _b$2) {
9153
9172
  return AISDKError.hasMarker(error, marker$2);
9154
9173
  }
9155
9174
  };
9175
+ var initialGlobalFetch = globalThis.fetch;
9176
+ isNodeDefaultFetch(initialGlobalFetch);
9177
+ function isNodeDefaultFetch(fetch) {
9178
+ const source = Function.prototype.toString.call(fetch);
9179
+ return source.includes("internal/deps/undici") || source.includes("lazy loading of undici");
9180
+ }
9181
+ function getCurrentModulePath() {
9182
+ const originalPrepareStackTrace = Error.prepareStackTrace;
9183
+ try {
9184
+ Error.prepareStackTrace = (_error, callSites) => callSites;
9185
+ const error = /* @__PURE__ */ new Error("Capture current module path");
9186
+ Error.captureStackTrace(error, getCurrentModulePath);
9187
+ const [caller] = error.stack;
9188
+ const fileName = caller == null ? void 0 : caller.getFileName();
9189
+ if (fileName == null) throw new Error("Unable to determine the current module path");
9190
+ return fileName;
9191
+ } finally {
9192
+ Error.prepareStackTrace = originalPrepareStackTrace;
9193
+ }
9194
+ }
9156
9195
  var DEFAULT_MAX_DOWNLOAD_SIZE = 2 * 1024 * 1024 * 1024;
9157
9196
  async function readResponseWithSizeLimit({ response, url, maxBytes = DEFAULT_MAX_DOWNLOAD_SIZE }) {
9158
9197
  const contentLength = response.headers.get("content-length");
@@ -9284,11 +9323,11 @@ function withUserAgentSuffix(headers, ...userAgentSuffixParts) {
9284
9323
  normalizedHeaders.set("user-agent", [currentUserAgentHeader, ...userAgentSuffixParts].filter(Boolean).join(" "));
9285
9324
  return Object.fromEntries(normalizedHeaders.entries());
9286
9325
  }
9287
- var VERSION$3 = "4.0.40";
9326
+ var VERSION$3 = "4.0.41";
9288
9327
  var getOriginalFetch = () => globalThis.fetch;
9289
- var getFromApi = async ({ url, headers = {}, successfulResponseHandler, failedResponseHandler, abortSignal, fetch: fetch2 = getOriginalFetch() }) => {
9328
+ var getFromApi = async ({ url, headers = {}, successfulResponseHandler, failedResponseHandler, abortSignal, fetch = getOriginalFetch() }) => {
9290
9329
  try {
9291
- const response = await fetch2(url, {
9330
+ const response = await fetch(url, {
9292
9331
  method: "GET",
9293
9332
  headers: withUserAgentSuffix(headers, `ai-sdk/provider-utils/${VERSION$3}`, getRuntimeEnvironmentUserAgent()),
9294
9333
  signal: abortSignal
@@ -10475,7 +10514,7 @@ function parseJsonEventStream({ stream, schema }) {
10475
10514
  } }));
10476
10515
  }
10477
10516
  var getOriginalFetch2 = () => globalThis.fetch;
10478
- var postJsonToApi = async ({ url, headers, body, failedResponseHandler, successfulResponseHandler, abortSignal, fetch: fetch2 }) => postToApi({
10517
+ var postJsonToApi = async ({ url, headers, body, failedResponseHandler, successfulResponseHandler, abortSignal, fetch }) => postToApi({
10479
10518
  url,
10480
10519
  headers: {
10481
10520
  "Content-Type": "application/json",
@@ -10488,11 +10527,11 @@ var postJsonToApi = async ({ url, headers, body, failedResponseHandler, successf
10488
10527
  failedResponseHandler,
10489
10528
  successfulResponseHandler,
10490
10529
  abortSignal,
10491
- fetch: fetch2
10530
+ fetch
10492
10531
  });
10493
- var postToApi = async ({ url, headers = {}, body, successfulResponseHandler, failedResponseHandler, abortSignal, fetch: fetch2 = getOriginalFetch2() }) => {
10532
+ var postToApi = async ({ url, headers = {}, body, successfulResponseHandler, failedResponseHandler, abortSignal, fetch = getOriginalFetch2() }) => {
10494
10533
  try {
10495
- const response = await fetch2(url, {
10534
+ const response = await fetch(url, {
10496
10535
  method: "POST",
10497
10536
  headers: withUserAgentSuffix(headers, `ai-sdk/provider-utils/${VERSION$3}`, getRuntimeEnvironmentUserAgent()),
10498
10537
  body: body.content,
@@ -10714,7 +10753,7 @@ function withoutTrailingSlash(url) {
10714
10753
  return url == null ? void 0 : url.replace(/\/$/, "");
10715
10754
  }
10716
10755
  //#endregion
10717
- //#region ../_vendored/ai_v6/dist/dist-iiYCn57Q.js
10756
+ //#region ../_vendored/ai_v6/dist/dist-3jq9sPhA.js
10718
10757
  function getContext() {
10719
10758
  return { headers: {} };
10720
10759
  }
@@ -12273,7 +12312,7 @@ async function getVercelRequestId() {
12273
12312
  var _a11;
12274
12313
  return (_a11 = getContext().headers) == null ? void 0 : _a11["x-vercel-id"];
12275
12314
  }
12276
- var VERSION$2 = "3.0.153";
12315
+ var VERSION$2 = "3.0.163";
12277
12316
  var AI_GATEWAY_PROTOCOL_VERSION = "0.0.1";
12278
12317
  function createGatewayProvider(options = {}) {
12279
12318
  var _a11, _b11;
@@ -13432,7 +13471,7 @@ function getTotalTimeoutMs(timeout) {
13432
13471
  if (typeof timeout === "number") return timeout;
13433
13472
  return timeout.totalMs;
13434
13473
  }
13435
- var VERSION = "6.0.230";
13474
+ var VERSION = "6.0.241";
13436
13475
  var dataContentSchema = z$1.union([
13437
13476
  z$1.string(),
13438
13477
  z$1.instanceof(Uint8Array),
@@ -20438,6 +20477,68 @@ function isMessageAtOrBeforeCursor(msg, cursor) {
20438
20477
  return false;
20439
20478
  }
20440
20479
  /**
20480
+ * Return the toolCallId of a tool-invocation part in the given state, or undefined.
20481
+ */
20482
+ function getToolInvocationId(part, state) {
20483
+ if (part?.type !== "tool-invocation") return void 0;
20484
+ if (part.toolInvocation.state !== state) return void 0;
20485
+ return part.toolInvocation.toolCallId || void 0;
20486
+ }
20487
+ function collectPendingToolResultIds(allMessages, observedIds) {
20488
+ const pendingToolResultIds = /* @__PURE__ */ new Set();
20489
+ for (const msg of allMessages) {
20490
+ if (!msg?.id) continue;
20491
+ if (observedIds?.has(msg.id)) continue;
20492
+ const parts = msg.content?.parts;
20493
+ if (!parts || !Array.isArray(parts)) continue;
20494
+ for (const part of parts) {
20495
+ const id = getToolInvocationId(part, "result");
20496
+ if (id) pendingToolResultIds.add(id);
20497
+ }
20498
+ }
20499
+ return pendingToolResultIds;
20500
+ }
20501
+ function hasPendingToolResultPair(message, pendingToolResultIds) {
20502
+ if (pendingToolResultIds.size === 0) return false;
20503
+ const parts = message.content?.parts;
20504
+ if (!parts || !Array.isArray(parts)) return false;
20505
+ return parts.some((part) => {
20506
+ const id = getToolInvocationId(part, "call");
20507
+ return id !== void 0 && pendingToolResultIds.has(id);
20508
+ });
20509
+ }
20510
+ function collectPendingToolResultIdsAfterMarker(allMessages, markerMessageIndex, markerMessage) {
20511
+ const pendingToolResultIds = /* @__PURE__ */ new Set();
20512
+ const unobservedMarkerParts = getUnobservedParts(markerMessage);
20513
+ if (unobservedMarkerParts.length > 0) collectPendingToolResultIds([{
20514
+ ...markerMessage,
20515
+ content: {
20516
+ ...markerMessage.content,
20517
+ parts: unobservedMarkerParts
20518
+ }
20519
+ }], void 0).forEach((id) => pendingToolResultIds.add(id));
20520
+ collectPendingToolResultIds(allMessages.slice(markerMessageIndex + 1), void 0).forEach((id) => pendingToolResultIds.add(id));
20521
+ return pendingToolResultIds;
20522
+ }
20523
+ function getUnobservedPartsPreservingToolCallPairs(message) {
20524
+ const parts = message.content?.parts;
20525
+ if (!parts || !Array.isArray(parts)) return [];
20526
+ const endMarkerIndex = findLastCompletedObservationBoundary(message);
20527
+ if (endMarkerIndex === -1) return getUnobservedParts(message);
20528
+ const unobservedParts = getUnobservedParts(message);
20529
+ const unobservedResultIds = /* @__PURE__ */ new Set();
20530
+ for (const part of unobservedParts) {
20531
+ const id = getToolInvocationId(part, "result");
20532
+ if (id) unobservedResultIds.add(id);
20533
+ }
20534
+ if (unobservedResultIds.size === 0) return unobservedParts;
20535
+ const preservedCalls = parts.slice(0, endMarkerIndex).filter((part) => {
20536
+ const id = getToolInvocationId(part, "call");
20537
+ return id !== void 0 && unobservedResultIds.has(id);
20538
+ });
20539
+ return preservedCalls.length > 0 ? [...preservedCalls, ...unobservedParts] : unobservedParts;
20540
+ }
20541
+ /**
20441
20542
  * Safely extract buffered observation chunks from a record.
20442
20543
  * Handles both array and JSON-string formats, returning empty array if malformed.
20443
20544
  */
@@ -20453,6 +20554,7 @@ function filterObservedMessages(opts) {
20453
20554
  const allMessages = messageList.get.all.db();
20454
20555
  const useMarkerBoundaryPruning = opts.useMarkerBoundaryPruning ?? true;
20455
20556
  const preserveMessageIds = opts.preserveMessageIds ?? /* @__PURE__ */ new Set();
20557
+ const observedIds = new Set(Array.isArray(record?.observedMessageIds) ? record.observedMessageIds : []);
20456
20558
  let markerMessageIndex = -1;
20457
20559
  let markerMessage = null;
20458
20560
  for (let i = allMessages.length - 1; i >= 0; i--) {
@@ -20465,33 +20567,40 @@ function filterObservedMessages(opts) {
20465
20567
  }
20466
20568
  }
20467
20569
  if (useMarkerBoundaryPruning && markerMessage && markerMessageIndex !== -1) {
20570
+ const pendingToolResultIds = collectPendingToolResultIdsAfterMarker(allMessages, markerMessageIndex, markerMessage);
20468
20571
  const messagesToRemove = [];
20469
20572
  for (let i = 0; i < markerMessageIndex; i++) {
20470
20573
  const msg = allMessages[i];
20471
- if (msg?.id && msg.id !== "om-continuation" && !preserveMessageIds.has(msg.id)) messagesToRemove.push(msg.id);
20574
+ if (msg?.id && msg.id !== "om-continuation" && !preserveMessageIds.has(msg.id) && !hasPendingToolResultPair(msg, pendingToolResultIds)) messagesToRemove.push(msg.id);
20472
20575
  }
20473
20576
  if (messagesToRemove.length > 0) messageList.removeByIds(messagesToRemove);
20474
- const unobserved = getUnobservedParts(markerMessage);
20577
+ const unobserved = getUnobservedPartsPreservingToolCallPairs(markerMessage);
20475
20578
  if (unobserved.length === 0) {
20476
20579
  if (markerMessage.id) messageList.removeByIds([markerMessage.id]);
20477
20580
  } else if (unobserved.length < (markerMessage.content?.parts?.length ?? 0)) markerMessage.content.parts = unobserved;
20478
20581
  } else if (record) {
20479
- const observedIds = new Set(Array.isArray(record.observedMessageIds) ? record.observedMessageIds : []);
20582
+ const pendingToolResultIds = collectPendingToolResultIds(allMessages, observedIds);
20480
20583
  const derivedCursor = opts.fallbackCursor ?? getLastObservedMessageCursor(allMessages.filter((msg) => !!msg?.id && observedIds.has(msg.id) && !!msg.createdAt));
20481
20584
  const lastObservedAt = record.lastObservedAt;
20482
20585
  const messagesToRemove = [];
20483
20586
  for (const msg of allMessages) {
20484
20587
  if (!msg?.id || msg.id === "om-continuation" || preserveMessageIds.has(msg.id)) continue;
20588
+ const hasPendingPair = hasPendingToolResultPair(msg, pendingToolResultIds);
20485
20589
  if (observedIds.has(msg.id)) {
20590
+ if (hasPendingPair) continue;
20486
20591
  messagesToRemove.push(msg.id);
20487
20592
  continue;
20488
20593
  }
20489
20594
  if (derivedCursor && isMessageAtOrBeforeCursor(msg, derivedCursor)) {
20595
+ if (hasPendingPair) continue;
20490
20596
  messagesToRemove.push(msg.id);
20491
20597
  continue;
20492
20598
  }
20493
20599
  if (lastObservedAt && msg.createdAt) {
20494
- if (new Date(msg.createdAt) <= lastObservedAt) messagesToRemove.push(msg.id);
20600
+ if (new Date(msg.createdAt) <= lastObservedAt) {
20601
+ if (hasPendingPair) continue;
20602
+ messagesToRemove.push(msg.id);
20603
+ }
20495
20604
  }
20496
20605
  }
20497
20606
  if (messagesToRemove.length > 0) messageList.removeByIds(messagesToRemove);
@@ -23797,6 +23906,14 @@ var ObservationalMemory = class ObservationalMemory {
23797
23906
  */
23798
23907
  locks = /* @__PURE__ */ new Map();
23799
23908
  /**
23909
+ * Initial record lookup/creation promises keyed by the effective storage scope.
23910
+ * Concurrent callers share the full read-or-create operation so a stale read
23911
+ * cannot create another generation-zero record after the first insert finishes.
23912
+ * Entries are removed after both success and failure so later calls always
23913
+ * re-read storage and transient failures can be retried.
23914
+ */
23915
+ recordInitializations = /* @__PURE__ */ new Map();
23916
+ /**
23800
23917
  * Acquire a lock for the given key, execute the callback, then release.
23801
23918
  * If a lock is already held, waits for it to be released before acquiring.
23802
23919
  */
@@ -24157,10 +24274,14 @@ var ObservationalMemory = class ObservationalMemory {
24157
24274
  */
24158
24275
  async getOrCreateRecord(threadId, resourceId) {
24159
24276
  const ids = this.getStorageIds(threadId, resourceId);
24160
- let record = await this.storage.getObservationalMemory(ids.threadId, ids.resourceId);
24161
- if (!record) {
24277
+ const initializationKey = ids.threadId === null ? `resource:${ids.resourceId}` : `thread:${ids.threadId}`;
24278
+ const pendingInitialization = this.recordInitializations.get(initializationKey);
24279
+ if (pendingInitialization) return pendingInitialization;
24280
+ const initialization = Promise.resolve().then(async () => {
24281
+ const record = await this.storage.getObservationalMemory(ids.threadId, ids.resourceId);
24282
+ if (record) return record;
24162
24283
  const observedTimezone = Intl.DateTimeFormat().resolvedOptions().timeZone;
24163
- record = await this.storage.initializeObservationalMemory({
24284
+ return this.storage.initializeObservationalMemory({
24164
24285
  threadId: ids.threadId,
24165
24286
  resourceId: ids.resourceId,
24166
24287
  scope: this.scope,
@@ -24171,8 +24292,13 @@ var ObservationalMemory = class ObservationalMemory {
24171
24292
  },
24172
24293
  observedTimezone
24173
24294
  });
24295
+ });
24296
+ this.recordInitializations.set(initializationKey, initialization);
24297
+ try {
24298
+ return await initialization;
24299
+ } finally {
24300
+ if (this.recordInitializations.get(initializationKey) === initialization) this.recordInitializations.delete(initializationKey);
24174
24301
  }
24175
- return record;
24176
24302
  }
24177
24303
  /**
24178
24304
  * Get current config snapshot for observation markers.
@@ -24510,7 +24636,13 @@ var ObservationalMemory = class ObservationalMemory {
24510
24636
  threadId: serialized.memoryInfo.threadId,
24511
24637
  resourceId: serialized.memoryInfo.resourceId
24512
24638
  };
24513
- if (this.scope === "thread") throw new Error("ObservationalMemory (scope: 'thread') requires a threadId, but none was found in RequestContext or MessageList. Ensure the agent is configured with Memory and a valid threadId is provided.");
24639
+ if (this.scope === "thread") throw new MastraError({
24640
+ id: "OBSERVATIONAL_MEMORY_THREAD_ID_REQUIRED",
24641
+ domain: ErrorDomain.MASTRA_MEMORY,
24642
+ category: ErrorCategory.USER,
24643
+ details: { status: 400 },
24644
+ text: "ObservationalMemory (scope: 'thread') requires a threadId, but none was found in RequestContext or MessageList. Ensure the agent is configured with Memory and a valid threadId is provided."
24645
+ });
24514
24646
  return null;
24515
24647
  }
24516
24648
  /**
@@ -26534,6 +26666,11 @@ function filterSystemReminderMessages(messages, includeSystemReminders) {
26534
26666
  if (includeSystemReminders) return messages;
26535
26667
  return messages.filter((message) => !isSystemReminderMessage(message));
26536
26668
  }
26669
+ function isTransientSignalMessage(message) {
26670
+ if (message.role !== "signal" || !isRecord(message.content)) return false;
26671
+ const metadata = message.content.metadata;
26672
+ return isRecord(metadata) && isRecord(metadata.signal) && !Array.isArray(metadata.signal) && metadata.signal.transient === true;
26673
+ }
26537
26674
  function normalizeObservationalMemoryConfig(config) {
26538
26675
  if (config === true) return { model: "google/gemini-2.5-flash" };
26539
26676
  if (config === false || config === void 0) return void 0;
@@ -27067,7 +27204,7 @@ ${workingMemory}`;
27067
27204
  async saveMessages({ messages, memoryConfig, observabilityContext }) {
27068
27205
  const span = this.createMemorySpan("save", observabilityContext, void 0, { messageCount: messages.length });
27069
27206
  try {
27070
- const updatedMessages = messages.filter((m) => m.role !== "system").map((m) => {
27207
+ const updatedMessages = messages.filter((m) => m.role !== "system" && !isTransientSignalMessage(m)).map((m) => {
27071
27208
  return this.updateMessageToHideWorkingMemoryV2(m);
27072
27209
  }).filter((m) => Boolean(m));
27073
27210
  const config = this.getMergedThreadConfig(memoryConfig);
@@ -27359,7 +27496,7 @@ ${workingMemory}`;
27359
27496
  */
27360
27497
  async persistMessages(messages) {
27361
27498
  if (messages.length === 0) return;
27362
- const persistableMessages = messages.filter((m) => m.role !== "system");
27499
+ const persistableMessages = messages.filter((m) => m.role !== "system" && !isTransientSignalMessage(m));
27363
27500
  if (persistableMessages.length === 0) return;
27364
27501
  await (await this.getMemoryStore()).saveMessages({ messages: persistableMessages });
27365
27502
  }
@@ -28306,4 +28443,4 @@ Notes:
28306
28443
  //#endregion
28307
28444
  export { extractCurrentTask as A, OBSERVATION_CONTEXT_INSTRUCTIONS as B, WorkingMemoryExtractor as C, OBSERVER_SYSTEM_PROMPT as D, TokenCounter as E, injectAnchorIds as F, OBSERVATION_CONTINUATION_HINT as H, parseAnchorId as I, stripEphemeralAnchorIds as L, hasCurrentTaskSection as M, optimizeObservationsForContext as N, buildObserverPrompt as O, parseObserverOutput as P, Extractor as R, deepMergeWorkingMemory as S, summarizeConversation as T, OBSERVATION_CONTEXT_PROMPT as V, reconcileObservationGroupsFromReflection as _, extractWorkingMemoryContent as a, wrapInObservationGroup as b, WORKING_MEMORY_STATE_ID as c, getObservationsAsOf as d, ObservationalMemoryProcessor as f, parseObservationGroups as g, deriveObservationGroupProvenance as h, WorkingMemory as i, formatMessagesForObserver as j, buildObserverSystemPrompt as k, WORKING_MEMORY_STATE_PROCESSOR_ID as l, combineObservationGroupRanges as m, MessageHistory$1 as n, extractWorkingMemoryTags as o, ObservationalMemory as p, SemanticRecall as r, removeWorkingMemoryTags as s, Memory as t, WorkingMemoryStateProcessor as u, renderObservationGroupsForReflection as v, SUMMARIZE_THREAD_DEFAULTS as w, ModelByInputTokens as x, stripObservationGroups as y, OBSERVATIONAL_MEMORY_DEFAULTS as z };
28308
28445
 
28309
- //# sourceMappingURL=src-BgdYYHLc.js.map
28446
+ //# sourceMappingURL=src-Cwt9gefz.js.map