misoai-web 1.5.7 → 1.5.9
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/es/agent.js +410 -25
- package/dist/es/agent.js.map +1 -1
- package/dist/es/bridge-mode-browser.js +3 -3
- package/dist/es/bridge-mode.js +412 -27
- package/dist/es/bridge-mode.js.map +1 -1
- package/dist/es/chrome-extension.js +411 -26
- package/dist/es/chrome-extension.js.map +1 -1
- package/dist/es/index.js +410 -25
- package/dist/es/index.js.map +1 -1
- package/dist/es/midscene-playground.js +410 -25
- package/dist/es/midscene-playground.js.map +1 -1
- package/dist/es/playground.js +410 -25
- package/dist/es/playground.js.map +1 -1
- package/dist/es/playwright.js +410 -25
- package/dist/es/playwright.js.map +1 -1
- package/dist/es/puppeteer-agent-launcher.js +410 -25
- package/dist/es/puppeteer-agent-launcher.js.map +1 -1
- package/dist/es/puppeteer.js +410 -25
- package/dist/es/puppeteer.js.map +1 -1
- package/dist/lib/agent.js +410 -25
- package/dist/lib/agent.js.map +1 -1
- package/dist/lib/bridge-mode-browser.js +3 -3
- package/dist/lib/bridge-mode.js +412 -27
- package/dist/lib/bridge-mode.js.map +1 -1
- package/dist/lib/chrome-extension.js +411 -26
- package/dist/lib/chrome-extension.js.map +1 -1
- package/dist/lib/index.js +410 -25
- package/dist/lib/index.js.map +1 -1
- package/dist/lib/midscene-playground.js +410 -25
- package/dist/lib/midscene-playground.js.map +1 -1
- package/dist/lib/playground.js +410 -25
- package/dist/lib/playground.js.map +1 -1
- package/dist/lib/playwright.js +410 -25
- package/dist/lib/playwright.js.map +1 -1
- package/dist/lib/puppeteer-agent-launcher.js +410 -25
- package/dist/lib/puppeteer-agent-launcher.js.map +1 -1
- package/dist/lib/puppeteer.js +410 -25
- package/dist/lib/puppeteer.js.map +1 -1
- package/dist/types/agent.d.ts +107 -2
- package/package.json +2 -2
@@ -628,6 +628,94 @@ var replanningCountLimit = 10;
|
|
628
628
|
var isAndroidPage = (page) => {
|
629
629
|
return page.pageType === "android";
|
630
630
|
};
|
631
|
+
var WorkflowMemory = class {
|
632
|
+
constructor(config) {
|
633
|
+
this.workflows = /* @__PURE__ */ new Map();
|
634
|
+
this.config = config;
|
635
|
+
}
|
636
|
+
/**
|
637
|
+
* İş akışı hafızasını getirir
|
638
|
+
*/
|
639
|
+
getWorkflowMemory(workflowId = "default") {
|
640
|
+
const workflow = this.workflows.get(workflowId);
|
641
|
+
return workflow?.memory || [];
|
642
|
+
}
|
643
|
+
/**
|
644
|
+
* İş akışı verilerini getirir
|
645
|
+
*/
|
646
|
+
getWorkflowData(workflowId = "default") {
|
647
|
+
return this.workflows.get(workflowId) || this.createEmptyWorkflowData(workflowId);
|
648
|
+
}
|
649
|
+
/**
|
650
|
+
* İş akışı hafızasını kaydeder
|
651
|
+
*/
|
652
|
+
saveWorkflowMemory(memory, workflowId = "default") {
|
653
|
+
const workflow = this.workflows.get(workflowId) || this.createEmptyWorkflowData(workflowId);
|
654
|
+
workflow.memory = [...memory];
|
655
|
+
workflow.metadata.totalSteps = workflow.steps.length;
|
656
|
+
workflow.metadata.completedSteps = workflow.steps.filter((s) => s.status === "completed").length;
|
657
|
+
workflow.metadata.failedSteps = workflow.steps.filter((s) => s.status === "failed").length;
|
658
|
+
this.workflows.set(workflowId, workflow);
|
659
|
+
this.enforceRetentionPolicy();
|
660
|
+
}
|
661
|
+
/**
|
662
|
+
* İş akışı bağlamını günceller
|
663
|
+
*/
|
664
|
+
updateWorkflowContext(context, workflowId = "default") {
|
665
|
+
const workflow = this.workflows.get(workflowId) || this.createEmptyWorkflowData(workflowId);
|
666
|
+
workflow.context = { ...workflow.context, ...context };
|
667
|
+
if (context.currentStep) {
|
668
|
+
const existingStep = workflow.steps.find((s) => s.stepName === context.currentStep);
|
669
|
+
if (!existingStep) {
|
670
|
+
workflow.steps.push({
|
671
|
+
stepId: `step_${workflow.steps.length + 1}`,
|
672
|
+
stepName: context.currentStep,
|
673
|
+
timestamp: context.timestamp,
|
674
|
+
status: "running",
|
675
|
+
memoryItems: []
|
676
|
+
});
|
677
|
+
}
|
678
|
+
}
|
679
|
+
this.workflows.set(workflowId, workflow);
|
680
|
+
}
|
681
|
+
/**
|
682
|
+
* İş akışını temizler
|
683
|
+
*/
|
684
|
+
clearWorkflow(workflowId = "default") {
|
685
|
+
this.workflows.delete(workflowId);
|
686
|
+
}
|
687
|
+
/**
|
688
|
+
* Tüm iş akışlarını temizler
|
689
|
+
*/
|
690
|
+
clearAll() {
|
691
|
+
this.workflows.clear();
|
692
|
+
}
|
693
|
+
createEmptyWorkflowData(workflowId) {
|
694
|
+
return {
|
695
|
+
workflowId,
|
696
|
+
steps: [],
|
697
|
+
memory: [],
|
698
|
+
context: {
|
699
|
+
pageInfo: { url: "", title: "" },
|
700
|
+
timestamp: Date.now()
|
701
|
+
},
|
702
|
+
metadata: {
|
703
|
+
totalSteps: 0,
|
704
|
+
completedSteps: 0,
|
705
|
+
failedSteps: 0,
|
706
|
+
startTime: Date.now()
|
707
|
+
}
|
708
|
+
};
|
709
|
+
}
|
710
|
+
enforceRetentionPolicy() {
|
711
|
+
const maxWorkflows = 10;
|
712
|
+
if (this.workflows.size > maxWorkflows) {
|
713
|
+
const sortedWorkflows = Array.from(this.workflows.entries()).sort(([, a], [, b]) => (b.metadata.endTime || b.metadata.startTime) - (a.metadata.endTime || a.metadata.startTime));
|
714
|
+
const toDelete = sortedWorkflows.slice(maxWorkflows);
|
715
|
+
toDelete.forEach(([workflowId]) => this.workflows.delete(workflowId));
|
716
|
+
}
|
717
|
+
}
|
718
|
+
};
|
631
719
|
var PageTaskExecutor = class {
|
632
720
|
constructor(page, insight, opts) {
|
633
721
|
this.conversationHistory = [];
|
@@ -635,6 +723,25 @@ var PageTaskExecutor = class {
|
|
635
723
|
this.insight = insight;
|
636
724
|
this.taskCache = opts.taskCache;
|
637
725
|
this.onTaskStartCallback = opts?.onTaskStart;
|
726
|
+
this.memoryConfig = {
|
727
|
+
maxItems: 100,
|
728
|
+
maxAge: 2 * 60 * 60 * 1e3,
|
729
|
+
// 2 saat
|
730
|
+
enablePersistence: true,
|
731
|
+
enableAnalytics: true,
|
732
|
+
filterStrategy: "hybrid",
|
733
|
+
...opts?.memoryConfig
|
734
|
+
};
|
735
|
+
this.sessionContext = {
|
736
|
+
sessionId: opts?.sessionId || this.generateSessionId(),
|
737
|
+
workflowId: opts?.workflowId,
|
738
|
+
startTime: Date.now(),
|
739
|
+
pageInfo: {
|
740
|
+
url: "",
|
741
|
+
title: ""
|
742
|
+
}
|
743
|
+
};
|
744
|
+
this.workflowMemory = new WorkflowMemory(this.memoryConfig);
|
638
745
|
}
|
639
746
|
async recordScreenshot(timing) {
|
640
747
|
const base64 = await this.page.screenshotBase64();
|
@@ -847,8 +954,11 @@ var PageTaskExecutor = class {
|
|
847
954
|
insightDump = dump;
|
848
955
|
};
|
849
956
|
this.insight.onceDumpUpdatedFn = dumpCollector;
|
957
|
+
const memoryContext = this.getMemoryAsContext();
|
850
958
|
const assertion = await this.insight.assert(
|
851
|
-
assertPlan.param.assertion
|
959
|
+
assertPlan.param.assertion,
|
960
|
+
memoryContext
|
961
|
+
// Hafıza bağlamını geç
|
852
962
|
);
|
853
963
|
if (!assertion.pass) {
|
854
964
|
if (plan2.type === "Assert") {
|
@@ -1334,25 +1444,146 @@ var PageTaskExecutor = class {
|
|
1334
1444
|
};
|
1335
1445
|
return task;
|
1336
1446
|
}
|
1447
|
+
/**
|
1448
|
+
* Persistent executor'ı getirir veya oluşturur
|
1449
|
+
*/
|
1450
|
+
getPersistentExecutor() {
|
1451
|
+
if (!this.persistentExecutor || this.persistentExecutor.status === "error") {
|
1452
|
+
const previousMemory = this.workflowMemory.getWorkflowMemory(this.sessionContext.workflowId);
|
1453
|
+
this.persistentExecutor = new Executor("Persistent Task Executor", {
|
1454
|
+
onTaskStart: this.onTaskStartCallback,
|
1455
|
+
initialMemory: previousMemory
|
1456
|
+
});
|
1457
|
+
}
|
1458
|
+
return this.persistentExecutor;
|
1459
|
+
}
|
1460
|
+
/**
|
1461
|
+
* Sayfa bağlamını günceller
|
1462
|
+
*/
|
1463
|
+
async updatePageContext() {
|
1464
|
+
try {
|
1465
|
+
if (this.page.url) {
|
1466
|
+
this.sessionContext.pageInfo.url = await this.page.url();
|
1467
|
+
}
|
1468
|
+
if (this.page.pageType === "puppeteer" || this.page.pageType === "playwright") {
|
1469
|
+
this.sessionContext.pageInfo.title = await this.page.title();
|
1470
|
+
}
|
1471
|
+
} catch (e) {
|
1472
|
+
}
|
1473
|
+
}
|
1474
|
+
/**
|
1475
|
+
* Hafızayı temizler
|
1476
|
+
*/
|
1477
|
+
clearMemory() {
|
1478
|
+
if (this.persistentExecutor) {
|
1479
|
+
this.persistentExecutor.clearMemory();
|
1480
|
+
}
|
1481
|
+
this.workflowMemory.clearWorkflow(this.sessionContext.workflowId || "default");
|
1482
|
+
}
|
1483
|
+
/**
|
1484
|
+
* Mevcut hafızayı döndürür
|
1485
|
+
*/
|
1486
|
+
getMemory() {
|
1487
|
+
return this.persistentExecutor?.getMemory() || [];
|
1488
|
+
}
|
1489
|
+
/**
|
1490
|
+
* İş akışı hafızasını döndürür
|
1491
|
+
*/
|
1492
|
+
getWorkflowMemory() {
|
1493
|
+
return this.workflowMemory.getWorkflowData(this.sessionContext.workflowId || "default");
|
1494
|
+
}
|
1495
|
+
/**
|
1496
|
+
* Hafıza istatistiklerini döndürür
|
1497
|
+
*/
|
1498
|
+
getMemoryStats() {
|
1499
|
+
return this.persistentExecutor?.getMemoryStats() || {
|
1500
|
+
totalItems: 0,
|
1501
|
+
analytics: { totalTasks: 0, memoryHits: 0, memoryMisses: 0, averageMemorySize: 0, memoryEffectiveness: 0 },
|
1502
|
+
config: this.memoryConfig
|
1503
|
+
};
|
1504
|
+
}
|
1505
|
+
/**
|
1506
|
+
* Hafıza konfigürasyonunu günceller
|
1507
|
+
*/
|
1508
|
+
updateMemoryConfig(config) {
|
1509
|
+
this.memoryConfig = { ...this.memoryConfig, ...config };
|
1510
|
+
if (this.persistentExecutor) {
|
1511
|
+
this.persistentExecutor.updateMemoryConfig(this.memoryConfig);
|
1512
|
+
}
|
1513
|
+
}
|
1514
|
+
/**
|
1515
|
+
* Oturum ID'sini oluşturur
|
1516
|
+
*/
|
1517
|
+
generateSessionId() {
|
1518
|
+
return `session_${Date.now()}_${Math.random().toString(36).substr(2, 8)}`;
|
1519
|
+
}
|
1520
|
+
/**
|
1521
|
+
* Hafızayı bağlam olarak formatlar
|
1522
|
+
*/
|
1523
|
+
getMemoryAsContext() {
|
1524
|
+
const memory = this.getMemory();
|
1525
|
+
if (memory.length === 0) {
|
1526
|
+
return "";
|
1527
|
+
}
|
1528
|
+
const recentMemory = memory.slice(-5);
|
1529
|
+
return recentMemory.map((item) => `- ${item.summary}`).join("\n");
|
1530
|
+
}
|
1337
1531
|
async runPlans(title, plans, opts) {
|
1338
|
-
|
1339
|
-
|
1340
|
-
|
1532
|
+
await this.updatePageContext();
|
1533
|
+
const useMemory = opts?.useMemory !== false;
|
1534
|
+
let taskExecutor;
|
1535
|
+
if (useMemory) {
|
1536
|
+
taskExecutor = this.getPersistentExecutor();
|
1537
|
+
this.workflowMemory.updateWorkflowContext({
|
1538
|
+
currentStep: title,
|
1539
|
+
pageInfo: this.sessionContext.pageInfo,
|
1540
|
+
timestamp: Date.now()
|
1541
|
+
}, this.sessionContext.workflowId || "default");
|
1542
|
+
} else {
|
1543
|
+
taskExecutor = new Executor(title, {
|
1544
|
+
onTaskStart: this.onTaskStartCallback
|
1545
|
+
});
|
1546
|
+
}
|
1341
1547
|
const { tasks } = await this.convertPlanToExecutable(plans, opts);
|
1548
|
+
tasks.forEach((task) => {
|
1549
|
+
task.context = {
|
1550
|
+
...task.context,
|
1551
|
+
...this.sessionContext.pageInfo,
|
1552
|
+
workflowId: this.sessionContext.workflowId,
|
1553
|
+
sessionId: this.sessionContext.sessionId
|
1554
|
+
};
|
1555
|
+
});
|
1342
1556
|
await taskExecutor.append(tasks);
|
1343
1557
|
const result = await taskExecutor.flush();
|
1558
|
+
if (useMemory) {
|
1559
|
+
this.workflowMemory.saveWorkflowMemory(
|
1560
|
+
taskExecutor.getMemory(),
|
1561
|
+
this.sessionContext.workflowId || "default"
|
1562
|
+
);
|
1563
|
+
}
|
1344
1564
|
return {
|
1345
1565
|
output: result,
|
1346
1566
|
executor: taskExecutor
|
1347
1567
|
};
|
1348
1568
|
}
|
1349
1569
|
async action(userPrompt, actionContext, opts) {
|
1350
|
-
const
|
1351
|
-
|
1352
|
-
|
1353
|
-
|
1570
|
+
const useMemory = true;
|
1571
|
+
let taskExecutor;
|
1572
|
+
if (useMemory) {
|
1573
|
+
taskExecutor = this.getPersistentExecutor();
|
1574
|
+
} else {
|
1575
|
+
taskExecutor = new Executor(taskTitleStr("Action", userPrompt), {
|
1576
|
+
onTaskStart: this.onTaskStartCallback
|
1577
|
+
});
|
1578
|
+
}
|
1579
|
+
const memoryContext = this.getMemoryAsContext();
|
1580
|
+
const initialLog = memoryContext ? memoryContext : void 0;
|
1581
|
+
let planningTask = this.planningTaskFromPrompt(userPrompt, initialLog, actionContext);
|
1354
1582
|
let replanCount = 0;
|
1355
1583
|
const logList = [];
|
1584
|
+
if (memoryContext) {
|
1585
|
+
logList.push(memoryContext);
|
1586
|
+
}
|
1356
1587
|
const yamlFlow = [];
|
1357
1588
|
while (planningTask) {
|
1358
1589
|
if (replanCount > replanningCountLimit) {
|
@@ -1462,15 +1693,21 @@ var PageTaskExecutor = class {
|
|
1462
1693
|
};
|
1463
1694
|
}
|
1464
1695
|
async createTypeQueryTask(type, demand, opt) {
|
1465
|
-
const
|
1466
|
-
|
1467
|
-
|
1468
|
-
|
1469
|
-
|
1470
|
-
|
1471
|
-
|
1472
|
-
|
1473
|
-
|
1696
|
+
const useMemory = true;
|
1697
|
+
let taskExecutor;
|
1698
|
+
if (useMemory) {
|
1699
|
+
taskExecutor = this.getPersistentExecutor();
|
1700
|
+
} else {
|
1701
|
+
taskExecutor = new Executor(
|
1702
|
+
taskTitleStr(
|
1703
|
+
type,
|
1704
|
+
typeof demand === "string" ? demand : JSON.stringify(demand)
|
1705
|
+
),
|
1706
|
+
{
|
1707
|
+
onTaskStart: this.onTaskStartCallback
|
1708
|
+
}
|
1709
|
+
);
|
1710
|
+
}
|
1474
1711
|
const queryTask = {
|
1475
1712
|
type: "Insight",
|
1476
1713
|
subType: type,
|
@@ -1492,9 +1729,12 @@ var PageTaskExecutor = class {
|
|
1492
1729
|
result: `${type}, ${demand}`
|
1493
1730
|
};
|
1494
1731
|
}
|
1732
|
+
const memoryContext = this.getMemoryAsContext();
|
1495
1733
|
const { data, usage } = await this.insight.extract(
|
1496
1734
|
demandInput,
|
1497
|
-
opt
|
1735
|
+
opt,
|
1736
|
+
memoryContext
|
1737
|
+
// Hafıza bağlamını geç
|
1498
1738
|
);
|
1499
1739
|
let outputResult = data;
|
1500
1740
|
if (ifTypeRestricted) {
|
@@ -1527,11 +1767,17 @@ var PageTaskExecutor = class {
|
|
1527
1767
|
async string(prompt, opt) {
|
1528
1768
|
return this.createTypeQueryTask("String", prompt, opt);
|
1529
1769
|
}
|
1530
|
-
async assert(assertion) {
|
1770
|
+
async assert(assertion, memoryContext) {
|
1531
1771
|
const description = `assert: ${assertion}`;
|
1532
|
-
const
|
1533
|
-
|
1534
|
-
|
1772
|
+
const useMemory = true;
|
1773
|
+
let taskExecutor;
|
1774
|
+
if (useMemory) {
|
1775
|
+
taskExecutor = this.getPersistentExecutor();
|
1776
|
+
} else {
|
1777
|
+
taskExecutor = new Executor(taskTitleStr("Assert", description), {
|
1778
|
+
onTaskStart: this.onTaskStartCallback
|
1779
|
+
});
|
1780
|
+
}
|
1535
1781
|
const assertionPlan = {
|
1536
1782
|
type: "Assert",
|
1537
1783
|
param: {
|
@@ -1741,7 +1987,7 @@ import yaml3 from "js-yaml";
|
|
1741
1987
|
import semver from "semver";
|
1742
1988
|
|
1743
1989
|
// package.json
|
1744
|
-
var version = "1.
|
1990
|
+
var version = "1.5.8";
|
1745
1991
|
|
1746
1992
|
// src/common/task-cache.ts
|
1747
1993
|
var debug3 = getDebug3("cache");
|
@@ -2228,7 +2474,13 @@ var PageAgent = class {
|
|
2228
2474
|
metadata: metadata2
|
2229
2475
|
};
|
2230
2476
|
}
|
2231
|
-
const
|
2477
|
+
const memoryContext = this.getMemoryAsContext();
|
2478
|
+
const enhancedActionContext = this.opts.aiActionContext ? `${this.opts.aiActionContext}
|
2479
|
+
|
2480
|
+
Previous workflow steps:
|
2481
|
+
${memoryContext}` : memoryContext ? `Previous workflow steps:
|
2482
|
+
${memoryContext}` : void 0;
|
2483
|
+
const { output, executor } = await (isVlmUiTars ? this.taskExecutor.actionToGoal(taskPrompt, { cacheable }) : this.taskExecutor.action(taskPrompt, enhancedActionContext, {
|
2232
2484
|
cacheable
|
2233
2485
|
}));
|
2234
2486
|
if (this.taskCache && output?.yamlFlow && cacheable !== false) {
|
@@ -2374,8 +2626,9 @@ var PageAgent = class {
|
|
2374
2626
|
} catch (e) {
|
2375
2627
|
}
|
2376
2628
|
}
|
2629
|
+
const memoryContext = this.getMemoryAsContext();
|
2377
2630
|
const assertionWithContext = currentUrl ? `For the page at URL "${currentUrl}", ${assertion}` : assertion;
|
2378
|
-
const { output, executor } = await this.taskExecutor.assert(assertionWithContext);
|
2631
|
+
const { output, executor } = await this.taskExecutor.assert(assertionWithContext, memoryContext);
|
2379
2632
|
const metadata = this.afterTaskRunning(executor, true);
|
2380
2633
|
if (output && opt?.keepRawResponse) {
|
2381
2634
|
return {
|
@@ -2622,6 +2875,138 @@ ${errors}`);
|
|
2622
2875
|
async destroy() {
|
2623
2876
|
await this.page.destroy();
|
2624
2877
|
}
|
2878
|
+
/**
|
2879
|
+
* Hafızayı bağlam olarak formatlar
|
2880
|
+
*/
|
2881
|
+
getMemoryAsContext() {
|
2882
|
+
const memory = this.taskExecutor.getMemory();
|
2883
|
+
if (memory.length === 0) {
|
2884
|
+
return "";
|
2885
|
+
}
|
2886
|
+
const recentMemory = memory.slice(-5);
|
2887
|
+
return recentMemory.map((item) => `- ${item.summary}`).join("\n");
|
2888
|
+
}
|
2889
|
+
/**
|
2890
|
+
* Mevcut hafızayı döndürür
|
2891
|
+
*/
|
2892
|
+
getMemory() {
|
2893
|
+
return this.taskExecutor.getMemory();
|
2894
|
+
}
|
2895
|
+
/**
|
2896
|
+
* Hafıza istatistiklerini döndürür
|
2897
|
+
*/
|
2898
|
+
getMemoryStats() {
|
2899
|
+
return this.taskExecutor.getMemoryStats();
|
2900
|
+
}
|
2901
|
+
/**
|
2902
|
+
* Hafızayı temizler
|
2903
|
+
*/
|
2904
|
+
clearMemory() {
|
2905
|
+
this.taskExecutor.clearMemory();
|
2906
|
+
}
|
2907
|
+
/**
|
2908
|
+
* Test sonunda kullanım için detaylı hafıza raporu döndürür (JSON formatında)
|
2909
|
+
*/
|
2910
|
+
getMemoryReport() {
|
2911
|
+
const memory = this.getMemory();
|
2912
|
+
const stats = this.getMemoryStats();
|
2913
|
+
return {
|
2914
|
+
summary: {
|
2915
|
+
totalItems: memory.length,
|
2916
|
+
totalTasks: stats.analytics.totalTasks,
|
2917
|
+
memoryHits: stats.analytics.memoryHits,
|
2918
|
+
memoryMisses: stats.analytics.memoryMisses,
|
2919
|
+
memoryEffectiveness: Math.round(stats.analytics.memoryEffectiveness * 100),
|
2920
|
+
averageMemorySize: Math.round(stats.analytics.averageMemorySize * 100) / 100
|
2921
|
+
},
|
2922
|
+
config: stats.config,
|
2923
|
+
items: memory.map((item) => ({
|
2924
|
+
id: item.id,
|
2925
|
+
timestamp: item.timestamp,
|
2926
|
+
taskType: item.taskType,
|
2927
|
+
summary: item.summary,
|
2928
|
+
context: item.context,
|
2929
|
+
metadata: item.metadata,
|
2930
|
+
tags: item.tags,
|
2931
|
+
relativeTime: this.formatRelativeTime(item.timestamp)
|
2932
|
+
})),
|
2933
|
+
analytics: {
|
2934
|
+
taskTypeDistribution: this.getTaskTypeDistribution(memory),
|
2935
|
+
successRate: this.calculateSuccessRate(memory),
|
2936
|
+
averageExecutionTime: this.calculateAverageExecutionTime(memory),
|
2937
|
+
dataExtractionCount: this.countDataExtractions(memory),
|
2938
|
+
workflowSteps: this.extractWorkflowSteps(memory)
|
2939
|
+
}
|
2940
|
+
};
|
2941
|
+
}
|
2942
|
+
/**
|
2943
|
+
* Test sonunda kullanım için basit hafıza özeti döndürür (JSON formatında)
|
2944
|
+
*/
|
2945
|
+
getMemorySummary() {
|
2946
|
+
const memory = this.getMemory();
|
2947
|
+
const stats = this.getMemoryStats();
|
2948
|
+
return {
|
2949
|
+
totalItems: memory.length,
|
2950
|
+
memoryEffectiveness: `${Math.round(stats.analytics.memoryEffectiveness * 100)}%`,
|
2951
|
+
taskTypes: this.getTaskTypeDistribution(memory),
|
2952
|
+
recentSteps: memory.slice(-5).map((item) => ({
|
2953
|
+
step: item.summary,
|
2954
|
+
type: item.taskType,
|
2955
|
+
success: item.metadata?.success || false,
|
2956
|
+
time: this.formatRelativeTime(item.timestamp)
|
2957
|
+
})),
|
2958
|
+
dataExtracted: this.getExtractedDataSummary(memory)
|
2959
|
+
};
|
2960
|
+
}
|
2961
|
+
formatRelativeTime(timestamp) {
|
2962
|
+
const now = Date.now();
|
2963
|
+
const diff = now - timestamp;
|
2964
|
+
const seconds = Math.floor(diff / 1e3);
|
2965
|
+
const minutes = Math.floor(seconds / 60);
|
2966
|
+
const hours = Math.floor(minutes / 60);
|
2967
|
+
if (hours > 0)
|
2968
|
+
return `${hours}h ${minutes % 60}m ago`;
|
2969
|
+
if (minutes > 0)
|
2970
|
+
return `${minutes}m ${seconds % 60}s ago`;
|
2971
|
+
return `${seconds}s ago`;
|
2972
|
+
}
|
2973
|
+
getTaskTypeDistribution(memory) {
|
2974
|
+
const distribution = {};
|
2975
|
+
memory.forEach((item) => {
|
2976
|
+
distribution[item.taskType] = (distribution[item.taskType] || 0) + 1;
|
2977
|
+
});
|
2978
|
+
return distribution;
|
2979
|
+
}
|
2980
|
+
calculateSuccessRate(memory) {
|
2981
|
+
if (memory.length === 0)
|
2982
|
+
return 0;
|
2983
|
+
const successCount = memory.filter((item) => item.metadata?.success !== false).length;
|
2984
|
+
return Math.round(successCount / memory.length * 100);
|
2985
|
+
}
|
2986
|
+
calculateAverageExecutionTime(memory) {
|
2987
|
+
const executionTimes = memory.map((item) => item.metadata?.executionTime).filter((time) => typeof time === "number");
|
2988
|
+
if (executionTimes.length === 0)
|
2989
|
+
return 0;
|
2990
|
+
const average = executionTimes.reduce((sum, time) => sum + time, 0) / executionTimes.length;
|
2991
|
+
return Math.round(average);
|
2992
|
+
}
|
2993
|
+
countDataExtractions(memory) {
|
2994
|
+
return memory.filter(
|
2995
|
+
(item) => item.context?.dataExtracted || item.taskType === "Insight" && item.summary.includes("Extracted")
|
2996
|
+
).length;
|
2997
|
+
}
|
2998
|
+
extractWorkflowSteps(memory) {
|
2999
|
+
return memory.map((item) => item.summary);
|
3000
|
+
}
|
3001
|
+
getExtractedDataSummary(memory) {
|
3002
|
+
const extractedData = {};
|
3003
|
+
memory.forEach((item, index) => {
|
3004
|
+
if (item.context?.dataExtracted) {
|
3005
|
+
extractedData[`step_${index + 1}`] = item.context.dataExtracted;
|
3006
|
+
}
|
3007
|
+
});
|
3008
|
+
return extractedData;
|
3009
|
+
}
|
2625
3010
|
};
|
2626
3011
|
|
2627
3012
|
// src/puppeteer/index.ts
|