@mastra/memory 1.0.0-beta.10 → 1.0.0-beta.11
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/CHANGELOG.md +87 -0
- package/dist/docs/README.md +36 -0
- package/dist/docs/SKILL.md +42 -0
- package/dist/docs/SOURCE_MAP.json +31 -0
- package/dist/docs/agents/01-agent-memory.md +160 -0
- package/dist/docs/agents/02-networks.md +236 -0
- package/dist/docs/agents/03-agent-approval.md +317 -0
- package/dist/docs/core/01-reference.md +114 -0
- package/dist/docs/memory/01-overview.md +76 -0
- package/dist/docs/memory/02-storage.md +181 -0
- package/dist/docs/memory/03-working-memory.md +386 -0
- package/dist/docs/memory/04-semantic-recall.md +235 -0
- package/dist/docs/memory/05-memory-processors.md +319 -0
- package/dist/docs/memory/06-reference.md +617 -0
- package/dist/docs/processors/01-reference.md +81 -0
- package/dist/docs/storage/01-reference.md +972 -0
- package/dist/docs/vectors/01-reference.md +929 -0
- package/dist/index.cjs +247 -14
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +134 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +247 -14
- package/dist/index.js.map +1 -1
- package/dist/tools/working-memory.d.ts +1 -1
- package/dist/tools/working-memory.d.ts.map +1 -1
- package/package.json +11 -10
package/dist/index.cjs
CHANGED
|
@@ -38,7 +38,7 @@ function _interopNamespace(e) {
|
|
|
38
38
|
var z4__namespace = /*#__PURE__*/_interopNamespace(z4);
|
|
39
39
|
var xxhash__default = /*#__PURE__*/_interopDefault(xxhash);
|
|
40
40
|
|
|
41
|
-
// ../_vendored/ai_v4/dist/chunk-
|
|
41
|
+
// ../_vendored/ai_v4/dist/chunk-OPIPXJLE.js
|
|
42
42
|
var __create = Object.create;
|
|
43
43
|
var __defProp = Object.defineProperty;
|
|
44
44
|
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
@@ -400,7 +400,7 @@ function getErrorMessage2(error) {
|
|
|
400
400
|
function isAbortError(error) {
|
|
401
401
|
return error instanceof Error && (error.name === "AbortError" || error.name === "TimeoutError");
|
|
402
402
|
}
|
|
403
|
-
var validatorSymbol = Symbol.for("vercel.ai.validator");
|
|
403
|
+
var validatorSymbol = /* @__PURE__ */ Symbol.for("vercel.ai.validator");
|
|
404
404
|
function validator(validate) {
|
|
405
405
|
return { [validatorSymbol]: true, validate };
|
|
406
406
|
}
|
|
@@ -458,7 +458,7 @@ function safeParseJSON({
|
|
|
458
458
|
};
|
|
459
459
|
}
|
|
460
460
|
}
|
|
461
|
-
var ignoreOverride = Symbol("Let zodToJsonSchema decide on which parser to use");
|
|
461
|
+
var ignoreOverride = /* @__PURE__ */ Symbol("Let zodToJsonSchema decide on which parser to use");
|
|
462
462
|
var defaultOptions = {
|
|
463
463
|
name: void 0,
|
|
464
464
|
$refStrategy: "root",
|
|
@@ -2266,7 +2266,7 @@ function zodSchema(zodSchema22, options) {
|
|
|
2266
2266
|
}
|
|
2267
2267
|
);
|
|
2268
2268
|
}
|
|
2269
|
-
var schemaSymbol = Symbol.for("vercel.ai.schema");
|
|
2269
|
+
var schemaSymbol = /* @__PURE__ */ Symbol.for("vercel.ai.schema");
|
|
2270
2270
|
function jsonSchema(jsonSchema22, {
|
|
2271
2271
|
validate
|
|
2272
2272
|
} = {}) {
|
|
@@ -2353,7 +2353,7 @@ function _makeCompatibilityCheck(ownVersion) {
|
|
|
2353
2353
|
}
|
|
2354
2354
|
var isCompatible = _makeCompatibilityCheck(VERSION);
|
|
2355
2355
|
var major = VERSION.split(".")[0];
|
|
2356
|
-
var GLOBAL_OPENTELEMETRY_API_KEY = Symbol.for("opentelemetry.js.api." + major);
|
|
2356
|
+
var GLOBAL_OPENTELEMETRY_API_KEY = /* @__PURE__ */ Symbol.for("opentelemetry.js.api." + major);
|
|
2357
2357
|
var _global = _globalThis;
|
|
2358
2358
|
function registerGlobal(type, instance, diag, allowOverride) {
|
|
2359
2359
|
var _a172;
|
|
@@ -4716,7 +4716,7 @@ function secureJsonParse(text4) {
|
|
|
4716
4716
|
Error.stackTraceLimit = stackTraceLimit;
|
|
4717
4717
|
}
|
|
4718
4718
|
}
|
|
4719
|
-
var validatorSymbol2 = Symbol.for("vercel.ai.validator");
|
|
4719
|
+
var validatorSymbol2 = /* @__PURE__ */ Symbol.for("vercel.ai.validator");
|
|
4720
4720
|
function validator2(validate) {
|
|
4721
4721
|
return { [validatorSymbol2]: true, validate };
|
|
4722
4722
|
}
|
|
@@ -5030,7 +5030,7 @@ var getRelativePath2 = (pathA, pathB) => {
|
|
|
5030
5030
|
}
|
|
5031
5031
|
return [(pathA.length - i).toString(), ...pathB.slice(i)].join("/");
|
|
5032
5032
|
};
|
|
5033
|
-
var ignoreOverride2 = Symbol(
|
|
5033
|
+
var ignoreOverride2 = /* @__PURE__ */ Symbol(
|
|
5034
5034
|
"Let zodToJsonSchema decide on which parser to use"
|
|
5035
5035
|
);
|
|
5036
5036
|
var defaultOptions2 = {
|
|
@@ -6150,7 +6150,7 @@ function zodSchema2(zodSchema22, options) {
|
|
|
6150
6150
|
return zod3Schema(zodSchema22);
|
|
6151
6151
|
}
|
|
6152
6152
|
}
|
|
6153
|
-
var schemaSymbol2 = Symbol.for("vercel.ai.schema");
|
|
6153
|
+
var schemaSymbol2 = /* @__PURE__ */ Symbol.for("vercel.ai.schema");
|
|
6154
6154
|
function jsonSchema2(jsonSchema22, {
|
|
6155
6155
|
validate
|
|
6156
6156
|
} = {}) {
|
|
@@ -6205,7 +6205,7 @@ var require_get_context = chunkSG3GRV3O_cjs.__commonJS({
|
|
|
6205
6205
|
getContext: () => getContext3
|
|
6206
6206
|
});
|
|
6207
6207
|
module.exports = __toCommonJS(get_context_exports);
|
|
6208
|
-
var SYMBOL_FOR_REQ_CONTEXT = Symbol.for("@vercel/request-context");
|
|
6208
|
+
var SYMBOL_FOR_REQ_CONTEXT = /* @__PURE__ */ Symbol.for("@vercel/request-context");
|
|
6209
6209
|
function getContext3() {
|
|
6210
6210
|
const fromSymbol = globalThis;
|
|
6211
6211
|
return fromSymbol[SYMBOL_FOR_REQ_CONTEXT]?.get?.() ?? {};
|
|
@@ -7234,7 +7234,7 @@ function _makeCompatibilityCheck2(ownVersion) {
|
|
|
7234
7234
|
}
|
|
7235
7235
|
var isCompatible2 = _makeCompatibilityCheck2(VERSION22);
|
|
7236
7236
|
var major2 = VERSION22.split(".")[0];
|
|
7237
|
-
var GLOBAL_OPENTELEMETRY_API_KEY2 = Symbol.for("opentelemetry.js.api." + major2);
|
|
7237
|
+
var GLOBAL_OPENTELEMETRY_API_KEY2 = /* @__PURE__ */ Symbol.for("opentelemetry.js.api." + major2);
|
|
7238
7238
|
var _global2 = _globalThis2;
|
|
7239
7239
|
function registerGlobal2(type, instance, diag, allowOverride) {
|
|
7240
7240
|
var _a162;
|
|
@@ -9680,7 +9680,7 @@ function addAdditionalPropertiesToJsonSchema(jsonSchema22) {
|
|
|
9680
9680
|
}
|
|
9681
9681
|
return jsonSchema22;
|
|
9682
9682
|
}
|
|
9683
|
-
var ignoreOverride3 = Symbol(
|
|
9683
|
+
var ignoreOverride3 = /* @__PURE__ */ Symbol(
|
|
9684
9684
|
"Let zodToJsonSchema decide on which parser to use"
|
|
9685
9685
|
);
|
|
9686
9686
|
var defaultOptions3 = {
|
|
@@ -10762,7 +10762,7 @@ var zod3ToJsonSchema = (schema, options) => {
|
|
|
10762
10762
|
combined.$schema = "http://json-schema.org/draft-07/schema#";
|
|
10763
10763
|
return combined;
|
|
10764
10764
|
};
|
|
10765
|
-
var schemaSymbol3 = Symbol.for("vercel.ai.schema");
|
|
10765
|
+
var schemaSymbol3 = /* @__PURE__ */ Symbol.for("vercel.ai.schema");
|
|
10766
10766
|
function lazySchema(createSchema) {
|
|
10767
10767
|
let schema;
|
|
10768
10768
|
return () => {
|
|
@@ -11163,7 +11163,7 @@ var require_get_context2 = chunkZUQPUTTO_cjs.__commonJS({
|
|
|
11163
11163
|
getContext: () => getContext3
|
|
11164
11164
|
});
|
|
11165
11165
|
module.exports = __toCommonJS(get_context_exports);
|
|
11166
|
-
var SYMBOL_FOR_REQ_CONTEXT = Symbol.for("@vercel/request-context");
|
|
11166
|
+
var SYMBOL_FOR_REQ_CONTEXT = /* @__PURE__ */ Symbol.for("@vercel/request-context");
|
|
11167
11167
|
function getContext3() {
|
|
11168
11168
|
const fromSymbol = globalThis;
|
|
11169
11169
|
return fromSymbol[SYMBOL_FOR_REQ_CONTEXT]?.get?.() ?? {};
|
|
@@ -12196,7 +12196,7 @@ function _makeCompatibilityCheck3(ownVersion) {
|
|
|
12196
12196
|
}
|
|
12197
12197
|
var isCompatible3 = _makeCompatibilityCheck3(VERSION23);
|
|
12198
12198
|
var major3 = VERSION23.split(".")[0];
|
|
12199
|
-
var GLOBAL_OPENTELEMETRY_API_KEY3 = Symbol.for("opentelemetry.js.api." + major3);
|
|
12199
|
+
var GLOBAL_OPENTELEMETRY_API_KEY3 = /* @__PURE__ */ Symbol.for("opentelemetry.js.api." + major3);
|
|
12200
12200
|
var _global3 = _globalThis3;
|
|
12201
12201
|
function registerGlobal3(type, instance, diag, allowOverride) {
|
|
12202
12202
|
var _a146;
|
|
@@ -14431,6 +14431,9 @@ var DefaultEmbedManyResult3 = class {
|
|
|
14431
14431
|
createIdGenerator3({ prefix: "aiobj", size: 24 });
|
|
14432
14432
|
createIdGenerator3({ prefix: "aiobj", size: 24 });
|
|
14433
14433
|
function deepMergeWorkingMemory(existing, update) {
|
|
14434
|
+
if (!update || typeof update !== "object" || Object.keys(update).length === 0) {
|
|
14435
|
+
return existing && typeof existing === "object" ? { ...existing } : {};
|
|
14436
|
+
}
|
|
14434
14437
|
if (!existing || typeof existing !== "object") {
|
|
14435
14438
|
return update;
|
|
14436
14439
|
}
|
|
@@ -14504,6 +14507,9 @@ var updateWorkingMemoryTool = (memoryConfig) => {
|
|
|
14504
14507
|
existingData = null;
|
|
14505
14508
|
}
|
|
14506
14509
|
}
|
|
14510
|
+
if (inputData.memory === void 0 || inputData.memory === null) {
|
|
14511
|
+
return { success: true, message: "No memory data provided, existing memory unchanged." };
|
|
14512
|
+
}
|
|
14507
14513
|
let newData;
|
|
14508
14514
|
if (typeof inputData.memory === "string") {
|
|
14509
14515
|
try {
|
|
@@ -15288,6 +15294,233 @@ ${template.content !== this.defaultWorkingMemoryTemplate ? `- Only store informa
|
|
|
15288
15294
|
const memoryStore = await this.getMemoryStore();
|
|
15289
15295
|
await memoryStore.deleteMessages(messageIds);
|
|
15290
15296
|
}
|
|
15297
|
+
/**
|
|
15298
|
+
* Clone a thread and its messages to create a new independent thread.
|
|
15299
|
+
* The cloned thread will have metadata tracking its source.
|
|
15300
|
+
*
|
|
15301
|
+
* If semantic recall is enabled, the cloned messages will also be embedded
|
|
15302
|
+
* and added to the vector store for semantic search.
|
|
15303
|
+
*
|
|
15304
|
+
* @param args - Clone configuration options
|
|
15305
|
+
* @param args.sourceThreadId - ID of the thread to clone
|
|
15306
|
+
* @param args.newThreadId - ID for the new cloned thread (if not provided, a random UUID will be generated)
|
|
15307
|
+
* @param args.resourceId - Resource ID for the new thread (defaults to source thread's resourceId)
|
|
15308
|
+
* @param args.title - Title for the new cloned thread
|
|
15309
|
+
* @param args.metadata - Additional metadata to merge with clone metadata
|
|
15310
|
+
* @param args.options - Options for filtering which messages to include
|
|
15311
|
+
* @param args.options.messageLimit - Maximum number of messages to copy (from most recent)
|
|
15312
|
+
* @param args.options.messageFilter - Filter messages by date range or specific IDs
|
|
15313
|
+
* @param memoryConfig - Optional memory configuration override
|
|
15314
|
+
* @returns The newly created thread and the cloned messages
|
|
15315
|
+
*
|
|
15316
|
+
* @example
|
|
15317
|
+
* ```typescript
|
|
15318
|
+
* // Clone entire thread
|
|
15319
|
+
* const { thread, clonedMessages } = await memory.cloneThread({
|
|
15320
|
+
* sourceThreadId: 'thread-123',
|
|
15321
|
+
* });
|
|
15322
|
+
*
|
|
15323
|
+
* // Clone with custom ID
|
|
15324
|
+
* const { thread, clonedMessages } = await memory.cloneThread({
|
|
15325
|
+
* sourceThreadId: 'thread-123',
|
|
15326
|
+
* newThreadId: 'my-custom-thread-id',
|
|
15327
|
+
* });
|
|
15328
|
+
*
|
|
15329
|
+
* // Clone with message limit
|
|
15330
|
+
* const { thread, clonedMessages } = await memory.cloneThread({
|
|
15331
|
+
* sourceThreadId: 'thread-123',
|
|
15332
|
+
* title: 'My cloned conversation',
|
|
15333
|
+
* options: {
|
|
15334
|
+
* messageLimit: 10, // Only clone last 10 messages
|
|
15335
|
+
* },
|
|
15336
|
+
* });
|
|
15337
|
+
*
|
|
15338
|
+
* // Clone with date filter
|
|
15339
|
+
* const { thread, clonedMessages } = await memory.cloneThread({
|
|
15340
|
+
* sourceThreadId: 'thread-123',
|
|
15341
|
+
* options: {
|
|
15342
|
+
* messageFilter: {
|
|
15343
|
+
* startDate: new Date('2024-01-01'),
|
|
15344
|
+
* endDate: new Date('2024-06-01'),
|
|
15345
|
+
* },
|
|
15346
|
+
* },
|
|
15347
|
+
* });
|
|
15348
|
+
* ```
|
|
15349
|
+
*/
|
|
15350
|
+
async cloneThread(args, memoryConfig) {
|
|
15351
|
+
const memoryStore = await this.getMemoryStore();
|
|
15352
|
+
const result = await memoryStore.cloneThread(args);
|
|
15353
|
+
const config = this.getMergedThreadConfig(memoryConfig);
|
|
15354
|
+
if (this.vector && config.semanticRecall && result.clonedMessages.length > 0) {
|
|
15355
|
+
await this.embedClonedMessages(result.clonedMessages, config);
|
|
15356
|
+
}
|
|
15357
|
+
return result;
|
|
15358
|
+
}
|
|
15359
|
+
/**
|
|
15360
|
+
* Embed cloned messages for semantic recall.
|
|
15361
|
+
* This is similar to the embedding logic in saveMessages but operates on already-saved messages.
|
|
15362
|
+
*/
|
|
15363
|
+
async embedClonedMessages(messages, config) {
|
|
15364
|
+
if (!this.vector || !this.embedder) {
|
|
15365
|
+
return;
|
|
15366
|
+
}
|
|
15367
|
+
const embeddingData = [];
|
|
15368
|
+
let dimension;
|
|
15369
|
+
await Promise.all(
|
|
15370
|
+
messages.map(async (message) => {
|
|
15371
|
+
let textForEmbedding = null;
|
|
15372
|
+
if (message.content?.content && typeof message.content.content === "string" && message.content.content.trim() !== "") {
|
|
15373
|
+
textForEmbedding = message.content.content;
|
|
15374
|
+
} else if (message.content?.parts && message.content.parts.length > 0) {
|
|
15375
|
+
const joined = message.content.parts.filter((part) => part.type === "text").map((part) => part.text).join(" ").trim();
|
|
15376
|
+
if (joined) textForEmbedding = joined;
|
|
15377
|
+
}
|
|
15378
|
+
if (!textForEmbedding) return;
|
|
15379
|
+
const result = await this.embedMessageContent(textForEmbedding);
|
|
15380
|
+
dimension = result.dimension;
|
|
15381
|
+
embeddingData.push({
|
|
15382
|
+
embeddings: result.embeddings,
|
|
15383
|
+
metadata: result.chunks.map(() => ({
|
|
15384
|
+
message_id: message.id,
|
|
15385
|
+
thread_id: message.threadId,
|
|
15386
|
+
resource_id: message.resourceId
|
|
15387
|
+
}))
|
|
15388
|
+
});
|
|
15389
|
+
})
|
|
15390
|
+
);
|
|
15391
|
+
if (embeddingData.length > 0 && dimension !== void 0) {
|
|
15392
|
+
const { indexName } = await this.createEmbeddingIndex(dimension, config);
|
|
15393
|
+
const allVectors = [];
|
|
15394
|
+
const allMetadata = [];
|
|
15395
|
+
for (const data of embeddingData) {
|
|
15396
|
+
allVectors.push(...data.embeddings);
|
|
15397
|
+
allMetadata.push(...data.metadata);
|
|
15398
|
+
}
|
|
15399
|
+
await this.vector.upsert({
|
|
15400
|
+
indexName,
|
|
15401
|
+
vectors: allVectors,
|
|
15402
|
+
metadata: allMetadata
|
|
15403
|
+
});
|
|
15404
|
+
}
|
|
15405
|
+
}
|
|
15406
|
+
/**
|
|
15407
|
+
* Get the clone metadata from a thread if it was cloned from another thread.
|
|
15408
|
+
*
|
|
15409
|
+
* @param thread - The thread to check
|
|
15410
|
+
* @returns The clone metadata if the thread is a clone, null otherwise
|
|
15411
|
+
*
|
|
15412
|
+
* @example
|
|
15413
|
+
* ```typescript
|
|
15414
|
+
* const thread = await memory.getThreadById({ threadId: 'thread-123' });
|
|
15415
|
+
* const cloneInfo = memory.getCloneMetadata(thread);
|
|
15416
|
+
* if (cloneInfo) {
|
|
15417
|
+
* console.log(`This thread was cloned from ${cloneInfo.sourceThreadId}`);
|
|
15418
|
+
* }
|
|
15419
|
+
* ```
|
|
15420
|
+
*/
|
|
15421
|
+
getCloneMetadata(thread) {
|
|
15422
|
+
if (!thread?.metadata?.clone) {
|
|
15423
|
+
return null;
|
|
15424
|
+
}
|
|
15425
|
+
return thread.metadata.clone;
|
|
15426
|
+
}
|
|
15427
|
+
/**
|
|
15428
|
+
* Check if a thread is a clone of another thread.
|
|
15429
|
+
*
|
|
15430
|
+
* @param thread - The thread to check
|
|
15431
|
+
* @returns True if the thread is a clone, false otherwise
|
|
15432
|
+
*
|
|
15433
|
+
* @example
|
|
15434
|
+
* ```typescript
|
|
15435
|
+
* const thread = await memory.getThreadById({ threadId: 'thread-123' });
|
|
15436
|
+
* if (memory.isClone(thread)) {
|
|
15437
|
+
* console.log('This is a cloned thread');
|
|
15438
|
+
* }
|
|
15439
|
+
* ```
|
|
15440
|
+
*/
|
|
15441
|
+
isClone(thread) {
|
|
15442
|
+
return this.getCloneMetadata(thread) !== null;
|
|
15443
|
+
}
|
|
15444
|
+
/**
|
|
15445
|
+
* Get the source thread that a cloned thread was created from.
|
|
15446
|
+
*
|
|
15447
|
+
* @param threadId - ID of the cloned thread
|
|
15448
|
+
* @returns The source thread if found, null if the thread is not a clone or source doesn't exist
|
|
15449
|
+
*
|
|
15450
|
+
* @example
|
|
15451
|
+
* ```typescript
|
|
15452
|
+
* const sourceThread = await memory.getSourceThread('cloned-thread-123');
|
|
15453
|
+
* if (sourceThread) {
|
|
15454
|
+
* console.log(`Original thread: ${sourceThread.title}`);
|
|
15455
|
+
* }
|
|
15456
|
+
* ```
|
|
15457
|
+
*/
|
|
15458
|
+
async getSourceThread(threadId) {
|
|
15459
|
+
const thread = await this.getThreadById({ threadId });
|
|
15460
|
+
const cloneMetadata = this.getCloneMetadata(thread);
|
|
15461
|
+
if (!cloneMetadata) {
|
|
15462
|
+
return null;
|
|
15463
|
+
}
|
|
15464
|
+
return this.getThreadById({ threadId: cloneMetadata.sourceThreadId });
|
|
15465
|
+
}
|
|
15466
|
+
/**
|
|
15467
|
+
* List all threads that were cloned from a specific source thread.
|
|
15468
|
+
*
|
|
15469
|
+
* @param sourceThreadId - ID of the source thread
|
|
15470
|
+
* @param resourceId - Optional resource ID to filter by
|
|
15471
|
+
* @returns Array of threads that are clones of the source thread
|
|
15472
|
+
*
|
|
15473
|
+
* @example
|
|
15474
|
+
* ```typescript
|
|
15475
|
+
* const clones = await memory.listClones('original-thread-123', 'user-456');
|
|
15476
|
+
* console.log(`Found ${clones.length} clones of this thread`);
|
|
15477
|
+
* ```
|
|
15478
|
+
*/
|
|
15479
|
+
async listClones(sourceThreadId, resourceId) {
|
|
15480
|
+
let targetResourceId = resourceId;
|
|
15481
|
+
if (!targetResourceId) {
|
|
15482
|
+
const sourceThread = await this.getThreadById({ threadId: sourceThreadId });
|
|
15483
|
+
if (!sourceThread) {
|
|
15484
|
+
return [];
|
|
15485
|
+
}
|
|
15486
|
+
targetResourceId = sourceThread.resourceId;
|
|
15487
|
+
}
|
|
15488
|
+
const { threads } = await this.listThreadsByResourceId({
|
|
15489
|
+
resourceId: targetResourceId,
|
|
15490
|
+
perPage: false
|
|
15491
|
+
// Get all threads
|
|
15492
|
+
});
|
|
15493
|
+
return threads.filter((thread) => {
|
|
15494
|
+
const cloneMetadata = this.getCloneMetadata(thread);
|
|
15495
|
+
return cloneMetadata?.sourceThreadId === sourceThreadId;
|
|
15496
|
+
});
|
|
15497
|
+
}
|
|
15498
|
+
/**
|
|
15499
|
+
* Get the clone history chain for a thread (all ancestors back to the original).
|
|
15500
|
+
*
|
|
15501
|
+
* @param threadId - ID of the thread to get history for
|
|
15502
|
+
* @returns Array of threads from oldest ancestor to the given thread (inclusive)
|
|
15503
|
+
*
|
|
15504
|
+
* @example
|
|
15505
|
+
* ```typescript
|
|
15506
|
+
* const history = await memory.getCloneHistory('deeply-cloned-thread');
|
|
15507
|
+
* // Returns: [originalThread, firstClone, secondClone, deeplyClonedThread]
|
|
15508
|
+
* ```
|
|
15509
|
+
*/
|
|
15510
|
+
async getCloneHistory(threadId) {
|
|
15511
|
+
const history = [];
|
|
15512
|
+
let currentThreadId = threadId;
|
|
15513
|
+
while (currentThreadId) {
|
|
15514
|
+
const thread = await this.getThreadById({ threadId: currentThreadId });
|
|
15515
|
+
if (!thread) {
|
|
15516
|
+
break;
|
|
15517
|
+
}
|
|
15518
|
+
history.unshift(thread);
|
|
15519
|
+
const cloneMetadata = this.getCloneMetadata(thread);
|
|
15520
|
+
currentThreadId = cloneMetadata?.sourceThreadId ?? null;
|
|
15521
|
+
}
|
|
15522
|
+
return history;
|
|
15523
|
+
}
|
|
15291
15524
|
};
|
|
15292
15525
|
|
|
15293
15526
|
Object.defineProperty(exports, "extractWorkingMemoryContent", {
|