js-agent-core 1.0.1
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/LICENSE +15 -0
- package/README.md +29 -0
- package/dist/core/AgentDashboard.d.ts +33 -0
- package/dist/core/AgentDashboard.d.ts.map +1 -0
- package/dist/core/AgentDashboard.js +477 -0
- package/dist/core/AgentDashboard.js.map +1 -0
- package/dist/core/AutoVectorStore.d.ts +23 -0
- package/dist/core/AutoVectorStore.d.ts.map +1 -0
- package/dist/core/AutoVectorStore.js +55 -0
- package/dist/core/AutoVectorStore.js.map +1 -0
- package/dist/core/BaseAgent.d.ts +70 -0
- package/dist/core/BaseAgent.d.ts.map +1 -0
- package/dist/core/BaseAgent.js +583 -0
- package/dist/core/BaseAgent.js.map +1 -0
- package/dist/core/EventEmitter.d.ts +8 -0
- package/dist/core/EventEmitter.d.ts.map +1 -0
- package/dist/core/EventEmitter.js +32 -0
- package/dist/core/EventEmitter.js.map +1 -0
- package/dist/core/LocalEmbedder.d.ts +25 -0
- package/dist/core/LocalEmbedder.d.ts.map +1 -0
- package/dist/core/LocalEmbedder.js +62 -0
- package/dist/core/LocalEmbedder.js.map +1 -0
- package/dist/core/LongTermMemory.d.ts +30 -0
- package/dist/core/LongTermMemory.d.ts.map +1 -0
- package/dist/core/LongTermMemory.js +123 -0
- package/dist/core/LongTermMemory.js.map +1 -0
- package/dist/core/MemoryVectorStore.d.ts +17 -0
- package/dist/core/MemoryVectorStore.d.ts.map +1 -0
- package/dist/core/MemoryVectorStore.js +44 -0
- package/dist/core/MemoryVectorStore.js.map +1 -0
- package/dist/core/OpenAIProvider.d.ts +21 -0
- package/dist/core/OpenAIProvider.d.ts.map +1 -0
- package/dist/core/OpenAIProvider.js +254 -0
- package/dist/core/OpenAIProvider.js.map +1 -0
- package/dist/core/SimpleMemory.d.ts +12 -0
- package/dist/core/SimpleMemory.d.ts.map +1 -0
- package/dist/core/SimpleMemory.js +27 -0
- package/dist/core/SimpleMemory.js.map +1 -0
- package/dist/core/StructuredPlanner.d.ts +13 -0
- package/dist/core/StructuredPlanner.d.ts.map +1 -0
- package/dist/core/StructuredPlanner.js +156 -0
- package/dist/core/StructuredPlanner.js.map +1 -0
- package/dist/core/ToolRegistry.d.ts +18 -0
- package/dist/core/ToolRegistry.d.ts.map +1 -0
- package/dist/core/ToolRegistry.js +74 -0
- package/dist/core/ToolRegistry.js.map +1 -0
- package/dist/core/index.d.ts +14 -0
- package/dist/core/index.d.ts.map +1 -0
- package/dist/core/index.js +14 -0
- package/dist/core/index.js.map +1 -0
- package/dist/core/logging/CompositeLogger.d.ts +8 -0
- package/dist/core/logging/CompositeLogger.d.ts.map +1 -0
- package/dist/core/logging/CompositeLogger.js +23 -0
- package/dist/core/logging/CompositeLogger.js.map +1 -0
- package/dist/core/logging/NodeFsLogger.d.ts +12 -0
- package/dist/core/logging/NodeFsLogger.d.ts.map +1 -0
- package/dist/core/logging/NodeFsLogger.js +46 -0
- package/dist/core/logging/NodeFsLogger.js.map +1 -0
- package/dist/core/logging/WebIndexedDbLogger.d.ts +15 -0
- package/dist/core/logging/WebIndexedDbLogger.d.ts.map +1 -0
- package/dist/core/logging/WebIndexedDbLogger.js +65 -0
- package/dist/core/logging/WebIndexedDbLogger.js.map +1 -0
- package/dist/core/logging/index.d.ts +11 -0
- package/dist/core/logging/index.d.ts.map +1 -0
- package/dist/core/logging/index.js +33 -0
- package/dist/core/logging/index.js.map +1 -0
- package/dist/core/persistence/NodeFsSkillStore.d.ts +17 -0
- package/dist/core/persistence/NodeFsSkillStore.d.ts.map +1 -0
- package/dist/core/persistence/NodeFsSkillStore.js +124 -0
- package/dist/core/persistence/NodeFsSkillStore.js.map +1 -0
- package/dist/core/persistence/NodeFsVectorStore.d.ts +25 -0
- package/dist/core/persistence/NodeFsVectorStore.d.ts.map +1 -0
- package/dist/core/persistence/NodeFsVectorStore.js +74 -0
- package/dist/core/persistence/NodeFsVectorStore.js.map +1 -0
- package/dist/core/persistence/SkillLoader.d.ts +26 -0
- package/dist/core/persistence/SkillLoader.d.ts.map +1 -0
- package/dist/core/persistence/SkillLoader.js +144 -0
- package/dist/core/persistence/SkillLoader.js.map +1 -0
- package/dist/core/persistence/WebIndexedDbSkillStore.d.ts +21 -0
- package/dist/core/persistence/WebIndexedDbSkillStore.d.ts.map +1 -0
- package/dist/core/persistence/WebIndexedDbSkillStore.js +119 -0
- package/dist/core/persistence/WebIndexedDbSkillStore.js.map +1 -0
- package/dist/core/persistence/WebIndexedDbVectorStore.d.ts +30 -0
- package/dist/core/persistence/WebIndexedDbVectorStore.d.ts.map +1 -0
- package/dist/core/persistence/WebIndexedDbVectorStore.js +87 -0
- package/dist/core/persistence/WebIndexedDbVectorStore.js.map +1 -0
- package/dist/core/persistence/index.d.ts +6 -0
- package/dist/core/persistence/index.d.ts.map +1 -0
- package/dist/core/persistence/index.js +21 -0
- package/dist/core/persistence/index.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +3 -0
- package/dist/index.js.map +1 -0
- package/dist/interfaces/IAgentEvent.d.ts +27 -0
- package/dist/interfaces/IAgentEvent.d.ts.map +1 -0
- package/dist/interfaces/IAgentEvent.js +2 -0
- package/dist/interfaces/IAgentEvent.js.map +1 -0
- package/dist/interfaces/IAgentState.d.ts +22 -0
- package/dist/interfaces/IAgentState.d.ts.map +1 -0
- package/dist/interfaces/IAgentState.js +2 -0
- package/dist/interfaces/IAgentState.js.map +1 -0
- package/dist/interfaces/ILLMProvider.d.ts +43 -0
- package/dist/interfaces/ILLMProvider.d.ts.map +1 -0
- package/dist/interfaces/ILLMProvider.js +2 -0
- package/dist/interfaces/ILLMProvider.js.map +1 -0
- package/dist/interfaces/ILogger.d.ts +15 -0
- package/dist/interfaces/ILogger.d.ts.map +1 -0
- package/dist/interfaces/ILogger.js +2 -0
- package/dist/interfaces/ILogger.js.map +1 -0
- package/dist/interfaces/IMemory.d.ts +32 -0
- package/dist/interfaces/IMemory.d.ts.map +1 -0
- package/dist/interfaces/IMemory.js +2 -0
- package/dist/interfaces/IMemory.js.map +1 -0
- package/dist/interfaces/IPlanner.d.ts +20 -0
- package/dist/interfaces/IPlanner.d.ts.map +1 -0
- package/dist/interfaces/IPlanner.js +2 -0
- package/dist/interfaces/IPlanner.js.map +1 -0
- package/dist/interfaces/ISkill.d.ts +9 -0
- package/dist/interfaces/ISkill.d.ts.map +1 -0
- package/dist/interfaces/ISkill.js +2 -0
- package/dist/interfaces/ISkill.js.map +1 -0
- package/dist/interfaces/ISkillStore.d.ts +53 -0
- package/dist/interfaces/ISkillStore.d.ts.map +1 -0
- package/dist/interfaces/ISkillStore.js +2 -0
- package/dist/interfaces/ISkillStore.js.map +1 -0
- package/dist/interfaces/ITool.d.ts +32 -0
- package/dist/interfaces/ITool.d.ts.map +1 -0
- package/dist/interfaces/ITool.js +2 -0
- package/dist/interfaces/ITool.js.map +1 -0
- package/dist/interfaces/index.d.ts +10 -0
- package/dist/interfaces/index.d.ts.map +1 -0
- package/dist/interfaces/index.js +10 -0
- package/dist/interfaces/index.js.map +1 -0
- package/package.json +47 -0
- package/src/core/AgentDashboard.ts +533 -0
- package/src/core/AutoVectorStore.ts +60 -0
- package/src/core/BaseAgent.ts +676 -0
- package/src/core/EventEmitter.ts +35 -0
- package/src/core/LocalEmbedder.ts +68 -0
- package/src/core/LongTermMemory.ts +146 -0
- package/src/core/MemoryVectorStore.ts +54 -0
- package/src/core/OpenAIProvider.ts +274 -0
- package/src/core/SimpleMemory.ts +31 -0
- package/src/core/StructuredPlanner.ts +165 -0
- package/src/core/ToolRegistry.ts +89 -0
- package/src/core/index.ts +16 -0
- package/src/core/logging/CompositeLogger.ts +26 -0
- package/src/core/logging/NodeFsLogger.ts +53 -0
- package/src/core/logging/WebIndexedDbLogger.ts +76 -0
- package/src/core/logging/index.ts +35 -0
- package/src/core/persistence/NodeFsSkillStore.ts +138 -0
- package/src/core/persistence/NodeFsVectorStore.ts +86 -0
- package/src/core/persistence/SkillLoader.ts +153 -0
- package/src/core/persistence/WebIndexedDbSkillStore.ts +139 -0
- package/src/core/persistence/WebIndexedDbVectorStore.ts +106 -0
- package/src/core/persistence/index.ts +22 -0
- package/src/index.ts +2 -0
- package/src/interfaces/IAgentEvent.ts +46 -0
- package/src/interfaces/IAgentState.ts +22 -0
- package/src/interfaces/ILLMProvider.ts +47 -0
- package/src/interfaces/ILogger.ts +16 -0
- package/src/interfaces/IMemory.ts +29 -0
- package/src/interfaces/IPlanner.ts +22 -0
- package/src/interfaces/ISkill.ts +9 -0
- package/src/interfaces/ISkillStore.ts +60 -0
- package/src/interfaces/ITool.ts +38 -0
- package/src/interfaces/index.ts +10 -0
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
export class LoggerFactory {
|
|
2
|
+
/**
|
|
3
|
+
* 根据当前运行环境创建默认的持久化日志记录器
|
|
4
|
+
*/
|
|
5
|
+
static async createDefaultLogger() {
|
|
6
|
+
// 1. 探测 Node.js 环境
|
|
7
|
+
if (typeof process !== 'undefined' && process.versions?.node) {
|
|
8
|
+
try {
|
|
9
|
+
const { NodeFsLogger } = await import('./NodeFsLogger.js');
|
|
10
|
+
return new NodeFsLogger();
|
|
11
|
+
}
|
|
12
|
+
catch (e) {
|
|
13
|
+
console.warn('Failed to initialize NodeFsLogger, falling back to console:', e);
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
// 2. 探测浏览器环境 (支持 IndexedDB)
|
|
17
|
+
if (typeof window !== 'undefined' && typeof indexedDB !== 'undefined') {
|
|
18
|
+
try {
|
|
19
|
+
const { WebIndexedDbLogger } = await import('./WebIndexedDbLogger.js');
|
|
20
|
+
return new WebIndexedDbLogger();
|
|
21
|
+
}
|
|
22
|
+
catch (e) {
|
|
23
|
+
console.warn('Failed to initialize WebIndexedDbLogger, falling back to console:', e);
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
// 3. 回退逻辑:如果没有任何持久化环境(如某些极简 Sandbox),返回 null,BaseAgent 会默认使用 console
|
|
27
|
+
return null;
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
export * from './NodeFsLogger.js';
|
|
31
|
+
export * from './WebIndexedDbLogger.js';
|
|
32
|
+
export * from './CompositeLogger.js';
|
|
33
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/core/logging/index.ts"],"names":[],"mappings":"AAEA,MAAM,OAAO,aAAa;IACxB;;OAEG;IACH,MAAM,CAAC,KAAK,CAAC,mBAAmB;QAC9B,mBAAmB;QACnB,IAAI,OAAO,OAAO,KAAK,WAAW,IAAI,OAAO,CAAC,QAAQ,EAAE,IAAI,EAAE,CAAC;YAC7D,IAAI,CAAC;gBACH,MAAM,EAAE,YAAY,EAAE,GAAG,MAAM,MAAM,CAAC,mBAAmB,CAAC,CAAC;gBAC3D,OAAO,IAAI,YAAY,EAAE,CAAC;YAC5B,CAAC;YAAC,OAAO,CAAC,EAAE,CAAC;gBACX,OAAO,CAAC,IAAI,CAAC,6DAA6D,EAAE,CAAC,CAAC,CAAC;YACjF,CAAC;QACH,CAAC;QAED,4BAA4B;QAC5B,IAAI,OAAO,MAAM,KAAK,WAAW,IAAI,OAAO,SAAS,KAAK,WAAW,EAAE,CAAC;YACtE,IAAI,CAAC;gBACH,MAAM,EAAE,kBAAkB,EAAE,GAAG,MAAM,MAAM,CAAC,yBAAyB,CAAC,CAAC;gBACvE,OAAO,IAAI,kBAAkB,EAAE,CAAC;YAClC,CAAC;YAAC,OAAO,CAAC,EAAE,CAAC;gBACX,OAAO,CAAC,IAAI,CAAC,mEAAmE,EAAE,CAAC,CAAC,CAAC;YACvF,CAAC;QACH,CAAC;QAED,qEAAqE;QACrE,OAAO,IAAI,CAAC;IACd,CAAC;CACF;AAED,cAAc,mBAAmB,CAAC;AAClC,cAAc,yBAAyB,CAAC;AACxC,cAAc,sBAAsB,CAAC"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { ISkillStore, SkillFile, SkillMetadata } from '../../interfaces/index.js';
|
|
2
|
+
/**
|
|
3
|
+
* 后端实现:基于文件系统的目录隔离存储
|
|
4
|
+
*/
|
|
5
|
+
export declare class NodeFsSkillStore implements ISkillStore {
|
|
6
|
+
private baseDir;
|
|
7
|
+
constructor(baseDir?: string);
|
|
8
|
+
private initDefaultDir;
|
|
9
|
+
private ensureDir;
|
|
10
|
+
private getSkillDir;
|
|
11
|
+
saveSkill(metadata: SkillMetadata, files: SkillFile[]): Promise<void>;
|
|
12
|
+
getSkillFiles(skillName: string): Promise<SkillFile[]>;
|
|
13
|
+
getSkillMetadata(skillName: string): Promise<SkillMetadata | null>;
|
|
14
|
+
listSkills(): Promise<SkillMetadata[]>;
|
|
15
|
+
deleteSkill(skillName: string): Promise<void>;
|
|
16
|
+
}
|
|
17
|
+
//# sourceMappingURL=NodeFsSkillStore.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"NodeFsSkillStore.d.ts","sourceRoot":"","sources":["../../../src/core/persistence/NodeFsSkillStore.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAElF;;GAEG;AACH,qBAAa,gBAAiB,YAAW,WAAW;IACtC,OAAO,CAAC,OAAO;gBAAP,OAAO,GAAE,MAAW;YAO1B,cAAc;YAOd,SAAS;YAST,WAAW;IAKnB,SAAS,CAAC,QAAQ,EAAE,aAAa,EAAE,KAAK,EAAE,SAAS,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC;IA0BrE,aAAa,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC;IAuCtD,gBAAgB,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,GAAG,IAAI,CAAC;IAalE,UAAU,IAAI,OAAO,CAAC,aAAa,EAAE,CAAC;IAgBtC,WAAW,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;CASpD"}
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 后端实现:基于文件系统的目录隔离存储
|
|
3
|
+
*/
|
|
4
|
+
export class NodeFsSkillStore {
|
|
5
|
+
baseDir;
|
|
6
|
+
constructor(baseDir = '') {
|
|
7
|
+
this.baseDir = baseDir;
|
|
8
|
+
if (!this.baseDir) {
|
|
9
|
+
// 延迟加载 path 以避免浏览器报错
|
|
10
|
+
this.initDefaultDir();
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
async initDefaultDir() {
|
|
14
|
+
if (typeof process !== 'undefined' && process.versions?.node) {
|
|
15
|
+
const path = await import('path');
|
|
16
|
+
this.baseDir = path.join(process.cwd(), 'storage', 'skills');
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
async ensureDir(dir) {
|
|
20
|
+
const fs = await import('fs/promises');
|
|
21
|
+
try {
|
|
22
|
+
await fs.access(dir);
|
|
23
|
+
}
|
|
24
|
+
catch {
|
|
25
|
+
await fs.mkdir(dir, { recursive: true });
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
async getSkillDir(skillName) {
|
|
29
|
+
const path = await import('path');
|
|
30
|
+
return path.join(this.baseDir, skillName);
|
|
31
|
+
}
|
|
32
|
+
async saveSkill(metadata, files) {
|
|
33
|
+
const fs = await import('fs/promises');
|
|
34
|
+
const path = await import('path');
|
|
35
|
+
const skillDir = await this.getSkillDir(metadata.name);
|
|
36
|
+
await this.ensureDir(skillDir);
|
|
37
|
+
// 1. 保存元数据
|
|
38
|
+
const metaPath = path.join(skillDir, 'metadata.json');
|
|
39
|
+
await fs.writeFile(metaPath, JSON.stringify(metadata, null, 2), 'utf-8');
|
|
40
|
+
// 2. 保存所有文件
|
|
41
|
+
for (const file of files) {
|
|
42
|
+
const filePath = path.join(skillDir, file.path);
|
|
43
|
+
const fileDir = path.dirname(filePath);
|
|
44
|
+
await this.ensureDir(fileDir);
|
|
45
|
+
if (typeof file.content === 'string') {
|
|
46
|
+
await fs.writeFile(filePath, file.content, 'utf-8');
|
|
47
|
+
}
|
|
48
|
+
else {
|
|
49
|
+
// Uint8Array is directly supported by fs.writeFile in Node.js
|
|
50
|
+
await fs.writeFile(filePath, file.content);
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
async getSkillFiles(skillName) {
|
|
55
|
+
const fs = await import('fs/promises');
|
|
56
|
+
const path = await import('path');
|
|
57
|
+
const skillDir = await this.getSkillDir(skillName);
|
|
58
|
+
const files = [];
|
|
59
|
+
const readDirRecursive = async (currentDir, relativePath = '') => {
|
|
60
|
+
const entries = await fs.readdir(currentDir, { withFileTypes: true });
|
|
61
|
+
for (const entry of entries) {
|
|
62
|
+
const fullPath = path.join(currentDir, entry.name);
|
|
63
|
+
const relPath = path.join(relativePath, entry.name);
|
|
64
|
+
if (entry.name === 'metadata.json' && relativePath === '')
|
|
65
|
+
continue; // 跳过元数据文件
|
|
66
|
+
if (entry.isDirectory()) {
|
|
67
|
+
await readDirRecursive(fullPath, relPath);
|
|
68
|
+
}
|
|
69
|
+
else {
|
|
70
|
+
const buffer = await fs.readFile(fullPath);
|
|
71
|
+
// Convert Buffer to Uint8Array to satisfy the interface
|
|
72
|
+
const content = new Uint8Array(buffer);
|
|
73
|
+
files.push({
|
|
74
|
+
path: relPath,
|
|
75
|
+
content: content
|
|
76
|
+
});
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
};
|
|
80
|
+
try {
|
|
81
|
+
await readDirRecursive(skillDir);
|
|
82
|
+
}
|
|
83
|
+
catch (e) {
|
|
84
|
+
console.error(`Failed to read files for skill ${skillName}:`, e);
|
|
85
|
+
}
|
|
86
|
+
return files;
|
|
87
|
+
}
|
|
88
|
+
async getSkillMetadata(skillName) {
|
|
89
|
+
const fs = await import('fs/promises');
|
|
90
|
+
const path = await import('path');
|
|
91
|
+
const metaPath = path.join(await this.getSkillDir(skillName), 'metadata.json');
|
|
92
|
+
try {
|
|
93
|
+
const content = await fs.readFile(metaPath, 'utf-8');
|
|
94
|
+
return JSON.parse(content);
|
|
95
|
+
}
|
|
96
|
+
catch {
|
|
97
|
+
return null;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
async listSkills() {
|
|
101
|
+
const fs = await import('fs/promises');
|
|
102
|
+
await this.ensureDir(this.baseDir);
|
|
103
|
+
const skillNames = await fs.readdir(this.baseDir);
|
|
104
|
+
const results = [];
|
|
105
|
+
for (const name of skillNames) {
|
|
106
|
+
const meta = await this.getSkillMetadata(name);
|
|
107
|
+
if (meta) {
|
|
108
|
+
results.push(meta);
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
return results;
|
|
112
|
+
}
|
|
113
|
+
async deleteSkill(skillName) {
|
|
114
|
+
const fs = await import('fs/promises');
|
|
115
|
+
const skillDir = await this.getSkillDir(skillName);
|
|
116
|
+
try {
|
|
117
|
+
await fs.rm(skillDir, { recursive: true, force: true });
|
|
118
|
+
}
|
|
119
|
+
catch (e) {
|
|
120
|
+
console.error(`Failed to delete skill ${skillName}:`, e);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
//# sourceMappingURL=NodeFsSkillStore.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"NodeFsSkillStore.js","sourceRoot":"","sources":["../../../src/core/persistence/NodeFsSkillStore.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { IVectorStore } from '../../interfaces/index.js';
|
|
2
|
+
export interface NodeFsVectorStoreOptions {
|
|
3
|
+
storagePath?: string;
|
|
4
|
+
}
|
|
5
|
+
export declare class NodeFsVectorStore implements IVectorStore {
|
|
6
|
+
private items;
|
|
7
|
+
private storagePath;
|
|
8
|
+
constructor(options?: NodeFsVectorStoreOptions);
|
|
9
|
+
private ensureDirectory;
|
|
10
|
+
private load;
|
|
11
|
+
private save;
|
|
12
|
+
add(text: string, embedding: number[], metadata?: Record<string, any>): Promise<void>;
|
|
13
|
+
search(queryEmbedding: number[], topK?: number): Promise<Array<{
|
|
14
|
+
text: string;
|
|
15
|
+
score: number;
|
|
16
|
+
metadata?: Record<string, any>;
|
|
17
|
+
}>>;
|
|
18
|
+
searchByKeyword(keyword: string, topK?: number): Promise<Array<{
|
|
19
|
+
text: string;
|
|
20
|
+
score: number;
|
|
21
|
+
metadata?: Record<string, any>;
|
|
22
|
+
}>>;
|
|
23
|
+
private cosineSimilarity;
|
|
24
|
+
}
|
|
25
|
+
//# sourceMappingURL=NodeFsVectorStore.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"NodeFsVectorStore.d.ts","sourceRoot":"","sources":["../../../src/core/persistence/NodeFsVectorStore.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AAIzD,MAAM,WAAW,wBAAwB;IACvC,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,qBAAa,iBAAkB,YAAW,YAAY;IACpD,OAAO,CAAC,KAAK,CAAoF;IACjG,OAAO,CAAC,WAAW,CAAS;gBAEhB,OAAO,GAAE,wBAA6B;YAIpC,eAAe;YASf,IAAI;YASJ,IAAI;IAKZ,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC;IAMrF,MAAM,CAAC,cAAc,EAAE,MAAM,EAAE,EAAE,IAAI,GAAE,MAAU,GAAG,OAAO,CAAC,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;KAAE,CAAC,CAAC;IAanI,eAAe,CAAC,OAAO,EAAE,MAAM,EAAE,IAAI,GAAE,MAAU,GAAG,OAAO,CAAC,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;KAAE,CAAC,CAAC;IAczI,OAAO,CAAC,gBAAgB;CAazB"}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import * as fs from 'fs/promises';
|
|
2
|
+
import * as path from 'path';
|
|
3
|
+
export class NodeFsVectorStore {
|
|
4
|
+
items = [];
|
|
5
|
+
storagePath;
|
|
6
|
+
constructor(options = {}) {
|
|
7
|
+
this.storagePath = options.storagePath || path.join(process.cwd(), '.agent_data', 'vector_store.json');
|
|
8
|
+
}
|
|
9
|
+
async ensureDirectory() {
|
|
10
|
+
const dir = path.dirname(this.storagePath);
|
|
11
|
+
try {
|
|
12
|
+
await fs.access(dir);
|
|
13
|
+
}
|
|
14
|
+
catch {
|
|
15
|
+
await fs.mkdir(dir, { recursive: true });
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
async load() {
|
|
19
|
+
try {
|
|
20
|
+
const data = await fs.readFile(this.storagePath, 'utf-8');
|
|
21
|
+
this.items = JSON.parse(data);
|
|
22
|
+
}
|
|
23
|
+
catch {
|
|
24
|
+
this.items = [];
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
async save() {
|
|
28
|
+
await this.ensureDirectory();
|
|
29
|
+
await fs.writeFile(this.storagePath, JSON.stringify(this.items, null, 2), 'utf-8');
|
|
30
|
+
}
|
|
31
|
+
async add(text, embedding, metadata) {
|
|
32
|
+
await this.load();
|
|
33
|
+
this.items.push({ text, embedding, metadata });
|
|
34
|
+
await this.save();
|
|
35
|
+
}
|
|
36
|
+
async search(queryEmbedding, topK = 3) {
|
|
37
|
+
await this.load();
|
|
38
|
+
const scoredItems = this.items.map(item => ({
|
|
39
|
+
...item,
|
|
40
|
+
score: this.cosineSimilarity(queryEmbedding, item.embedding)
|
|
41
|
+
}));
|
|
42
|
+
return scoredItems
|
|
43
|
+
.sort((a, b) => b.score - a.score)
|
|
44
|
+
.slice(0, topK)
|
|
45
|
+
.map(({ text, score, metadata }) => ({ text, score, metadata }));
|
|
46
|
+
}
|
|
47
|
+
async searchByKeyword(keyword, topK = 3) {
|
|
48
|
+
await this.load();
|
|
49
|
+
const lowKeyword = keyword.toLowerCase();
|
|
50
|
+
return this.items
|
|
51
|
+
.filter(item => item.text.toLowerCase().includes(lowKeyword))
|
|
52
|
+
.map(item => ({
|
|
53
|
+
text: item.text,
|
|
54
|
+
score: 1.0,
|
|
55
|
+
metadata: item.metadata
|
|
56
|
+
}))
|
|
57
|
+
.slice(0, topK);
|
|
58
|
+
}
|
|
59
|
+
cosineSimilarity(vecA, vecB) {
|
|
60
|
+
if (vecA.length !== vecB.length)
|
|
61
|
+
return 0;
|
|
62
|
+
let dotProduct = 0;
|
|
63
|
+
let normA = 0;
|
|
64
|
+
let normB = 0;
|
|
65
|
+
for (let i = 0; i < vecA.length; i++) {
|
|
66
|
+
dotProduct += vecA[i] * vecB[i];
|
|
67
|
+
normA += vecA[i] * vecA[i];
|
|
68
|
+
normB += vecB[i] * vecB[i];
|
|
69
|
+
}
|
|
70
|
+
const magnitude = Math.sqrt(normA) * Math.sqrt(normB);
|
|
71
|
+
return magnitude === 0 ? 0 : dotProduct / magnitude;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
//# sourceMappingURL=NodeFsVectorStore.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"NodeFsVectorStore.js","sourceRoot":"","sources":["../../../src/core/persistence/NodeFsVectorStore.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,MAAM,aAAa,CAAC;AAClC,OAAO,KAAK,IAAI,MAAM,MAAM,CAAC;AAM7B,MAAM,OAAO,iBAAiB;IACpB,KAAK,GAAiF,EAAE,CAAC;IACzF,WAAW,CAAS;IAE5B,YAAY,UAAoC,EAAE;QAChD,IAAI,CAAC,WAAW,GAAG,OAAO,CAAC,WAAW,IAAI,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,EAAE,mBAAmB,CAAC,CAAC;IACzG,CAAC;IAEO,KAAK,CAAC,eAAe;QAC3B,MAAM,GAAG,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;QAC3C,IAAI,CAAC;YACH,MAAM,EAAE,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;QACvB,CAAC;QAAC,MAAM,CAAC;YACP,MAAM,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;QAC3C,CAAC;IACH,CAAC;IAEO,KAAK,CAAC,IAAI;QAChB,IAAI,CAAC;YACH,MAAM,IAAI,GAAG,MAAM,EAAE,CAAC,QAAQ,CAAC,IAAI,CAAC,WAAW,EAAE,OAAO,CAAC,CAAC;YAC1D,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;QAChC,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,KAAK,GAAG,EAAE,CAAC;QAClB,CAAC;IACH,CAAC;IAEO,KAAK,CAAC,IAAI;QAChB,MAAM,IAAI,CAAC,eAAe,EAAE,CAAC;QAC7B,MAAM,EAAE,CAAC,SAAS,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC;IACrF,CAAC;IAED,KAAK,CAAC,GAAG,CAAC,IAAY,EAAE,SAAmB,EAAE,QAA8B;QACzE,MAAM,IAAI,CAAC,IAAI,EAAE,CAAC;QAClB,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,QAAQ,EAAE,CAAC,CAAC;QAC/C,MAAM,IAAI,CAAC,IAAI,EAAE,CAAC;IACpB,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,cAAwB,EAAE,OAAe,CAAC;QACrD,MAAM,IAAI,CAAC,IAAI,EAAE,CAAC;QAClB,MAAM,WAAW,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;YAC1C,GAAG,IAAI;YACP,KAAK,EAAE,IAAI,CAAC,gBAAgB,CAAC,cAAc,EAAE,IAAI,CAAC,SAAS,CAAC;SAC7D,CAAC,CAAC,CAAC;QAEJ,OAAO,WAAW;aACf,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,KAAK,CAAC;aACjC,KAAK,CAAC,CAAC,EAAE,IAAI,CAAC;aACd,GAAG,CAAC,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,QAAQ,EAAE,CAAC,CAAC,CAAC;IACrE,CAAC;IAED,KAAK,CAAC,eAAe,CAAC,OAAe,EAAE,OAAe,CAAC;QACrD,MAAM,IAAI,CAAC,IAAI,EAAE,CAAC;QAClB,MAAM,UAAU,GAAG,OAAO,CAAC,WAAW,EAAE,CAAC;QAEzC,OAAO,IAAI,CAAC,KAAK;aACd,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,WAAW,EAAE,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;aAC5D,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;YACZ,IAAI,EAAE,IAAI,CAAC,IAAI;YACf,KAAK,EAAE,GAAG;YACV,QAAQ,EAAE,IAAI,CAAC,QAAQ;SACxB,CAAC,CAAC;aACF,KAAK,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC;IACpB,CAAC;IAEO,gBAAgB,CAAC,IAAc,EAAE,IAAc;QACrD,IAAI,IAAI,CAAC,MAAM,KAAK,IAAI,CAAC,MAAM;YAAE,OAAO,CAAC,CAAC;QAC1C,IAAI,UAAU,GAAG,CAAC,CAAC;QACnB,IAAI,KAAK,GAAG,CAAC,CAAC;QACd,IAAI,KAAK,GAAG,CAAC,CAAC;QACd,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;YACrC,UAAU,IAAI,IAAI,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;YAChC,KAAK,IAAI,IAAI,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;YAC3B,KAAK,IAAI,IAAI,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;QAC7B,CAAC;QACD,MAAM,SAAS,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACtD,OAAO,SAAS,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,UAAU,GAAG,SAAS,CAAC;IACtD,CAAC;CACF"}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { ISkill, SkillFile, SkillMetadata } from '../../interfaces/index.js';
|
|
2
|
+
/**
|
|
3
|
+
* 环境感知型技能加载器
|
|
4
|
+
*/
|
|
5
|
+
export declare class SkillLoader {
|
|
6
|
+
/**
|
|
7
|
+
* 将技能代码和元数据转化为可执行的 ISkill 或 ITool
|
|
8
|
+
* @param metadata 技能元数据
|
|
9
|
+
* @param files 技能文件列表
|
|
10
|
+
* @param baseDir 可选的基础目录 (用于 Node.js 子进程定位文件)
|
|
11
|
+
*/
|
|
12
|
+
static load(metadata: SkillMetadata, files: SkillFile[], baseDir?: string): Promise<ISkill>;
|
|
13
|
+
/**
|
|
14
|
+
* 加载 JavaScript 技能
|
|
15
|
+
*/
|
|
16
|
+
private static loadJavascript;
|
|
17
|
+
/**
|
|
18
|
+
* 加载脚本代理 (Python, Bash)
|
|
19
|
+
*/
|
|
20
|
+
private static loadScriptProxy;
|
|
21
|
+
/**
|
|
22
|
+
* 加载 WebAssembly 技能 (示意实现)
|
|
23
|
+
*/
|
|
24
|
+
private static loadWasm;
|
|
25
|
+
}
|
|
26
|
+
//# sourceMappingURL=SkillLoader.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SkillLoader.d.ts","sourceRoot":"","sources":["../../../src/core/persistence/SkillLoader.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAS,SAAS,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAGpF;;GAEG;AACH,qBAAa,WAAW;IACtB;;;;;OAKG;WACU,IAAI,CAAC,QAAQ,EAAE,aAAa,EAAE,KAAK,EAAE,SAAS,EAAE,EAAE,OAAO,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAmBjG;;OAEG;mBACkB,cAAc;IAqCnC;;OAEG;mBACkB,eAAe;IA8CpC;;OAEG;mBACkB,QAAQ;CA4B9B"}
|
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
/**
|
|
3
|
+
* 环境感知型技能加载器
|
|
4
|
+
*/
|
|
5
|
+
export class SkillLoader {
|
|
6
|
+
/**
|
|
7
|
+
* 将技能代码和元数据转化为可执行的 ISkill 或 ITool
|
|
8
|
+
* @param metadata 技能元数据
|
|
9
|
+
* @param files 技能文件列表
|
|
10
|
+
* @param baseDir 可选的基础目录 (用于 Node.js 子进程定位文件)
|
|
11
|
+
*/
|
|
12
|
+
static async load(metadata, files, baseDir) {
|
|
13
|
+
const isWeb = typeof window !== 'undefined';
|
|
14
|
+
switch (metadata.runtime) {
|
|
15
|
+
case 'javascript':
|
|
16
|
+
return await this.loadJavascript(metadata, files, baseDir);
|
|
17
|
+
case 'python':
|
|
18
|
+
case 'bash':
|
|
19
|
+
if (isWeb) {
|
|
20
|
+
throw new Error(`Runtime ${metadata.runtime} is not supported in the browser.`);
|
|
21
|
+
}
|
|
22
|
+
return await this.loadScriptProxy(metadata, files, baseDir);
|
|
23
|
+
case 'wasm':
|
|
24
|
+
return await this.loadWasm(metadata, files);
|
|
25
|
+
default:
|
|
26
|
+
throw new Error(`Unsupported runtime: ${metadata.runtime}`);
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* 加载 JavaScript 技能
|
|
31
|
+
*/
|
|
32
|
+
static async loadJavascript(metadata, files, baseDir) {
|
|
33
|
+
const entryFile = files.find(f => f.path === metadata.entry);
|
|
34
|
+
if (!entryFile)
|
|
35
|
+
throw new Error(`Entry file ${metadata.entry} not found.`);
|
|
36
|
+
if (typeof window !== 'undefined') {
|
|
37
|
+
// Web 环境: 使用 Blob URL
|
|
38
|
+
const code = typeof entryFile.content === 'string'
|
|
39
|
+
? entryFile.content
|
|
40
|
+
: new TextDecoder().decode(entryFile.content);
|
|
41
|
+
const blob = new Blob([code], { type: 'text/javascript' });
|
|
42
|
+
const url = URL.createObjectURL(blob);
|
|
43
|
+
try {
|
|
44
|
+
const module = await import(url);
|
|
45
|
+
return module.default || module;
|
|
46
|
+
}
|
|
47
|
+
finally {
|
|
48
|
+
URL.revokeObjectURL(url);
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
else {
|
|
52
|
+
// Node.js 环境: 优先从磁盘路径加载 (支持断点调试和完整模块解析)
|
|
53
|
+
if (baseDir) {
|
|
54
|
+
const path = await import('path');
|
|
55
|
+
const fullPath = path.join(baseDir, metadata.name, metadata.entry);
|
|
56
|
+
const module = await import(`file://${fullPath}`);
|
|
57
|
+
return module.default || module;
|
|
58
|
+
}
|
|
59
|
+
// 如果没有 baseDir (如内存模式),回退到 data URI
|
|
60
|
+
const code = typeof entryFile.content === 'string'
|
|
61
|
+
? entryFile.content
|
|
62
|
+
: new TextDecoder().decode(entryFile.content);
|
|
63
|
+
const base64Code = Buffer.from(code).toString('base64');
|
|
64
|
+
const dataUri = `data:text/javascript;base64,${base64Code}`;
|
|
65
|
+
const module = await import(dataUri);
|
|
66
|
+
return module.default || module;
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* 加载脚本代理 (Python, Bash)
|
|
71
|
+
*/
|
|
72
|
+
static async loadScriptProxy(metadata, files, baseDir) {
|
|
73
|
+
const { spawn } = await import('child_process');
|
|
74
|
+
const path = await import('path');
|
|
75
|
+
// 脚本代理 Skill
|
|
76
|
+
return {
|
|
77
|
+
name: metadata.name,
|
|
78
|
+
description: metadata.description,
|
|
79
|
+
tools: [{
|
|
80
|
+
name: metadata.name,
|
|
81
|
+
description: metadata.description,
|
|
82
|
+
parameters: metadata.parameters || z.any(),
|
|
83
|
+
execute: async (params) => {
|
|
84
|
+
const scriptPath = path.join(baseDir, metadata.name, metadata.entry);
|
|
85
|
+
return new Promise((resolve) => {
|
|
86
|
+
const runtime = metadata.runtime === 'python' ? 'python3' : 'bash';
|
|
87
|
+
const child = spawn(runtime, [scriptPath]);
|
|
88
|
+
// 发送参数
|
|
89
|
+
child.stdin.write(JSON.stringify(params));
|
|
90
|
+
child.stdin.end();
|
|
91
|
+
let stdout = '';
|
|
92
|
+
let stderr = '';
|
|
93
|
+
child.stdout.on('data', (data) => stdout += data);
|
|
94
|
+
child.stderr.on('data', (data) => stderr += data);
|
|
95
|
+
child.on('close', (code) => {
|
|
96
|
+
if (code !== 0) {
|
|
97
|
+
resolve({ success: false, error: `Script exited with code ${code}: ${stderr}` });
|
|
98
|
+
}
|
|
99
|
+
else {
|
|
100
|
+
try {
|
|
101
|
+
const result = JSON.parse(stdout);
|
|
102
|
+
resolve({ success: true, data: result });
|
|
103
|
+
}
|
|
104
|
+
catch {
|
|
105
|
+
resolve({ success: true, data: stdout.trim() });
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
});
|
|
109
|
+
});
|
|
110
|
+
}
|
|
111
|
+
}]
|
|
112
|
+
};
|
|
113
|
+
}
|
|
114
|
+
/**
|
|
115
|
+
* 加载 WebAssembly 技能 (示意实现)
|
|
116
|
+
*/
|
|
117
|
+
static async loadWasm(metadata, files) {
|
|
118
|
+
const entryFile = files.find(f => f.path === metadata.entry);
|
|
119
|
+
if (!entryFile)
|
|
120
|
+
throw new Error(`WASM entry ${metadata.entry} not found.`);
|
|
121
|
+
const buffer = typeof entryFile.content === 'string'
|
|
122
|
+
? new TextEncoder().encode(entryFile.content)
|
|
123
|
+
: entryFile.content;
|
|
124
|
+
const wasmModule = await WebAssembly.instantiate(buffer);
|
|
125
|
+
const exports = wasmModule.instance?.exports || wasmModule.exports;
|
|
126
|
+
return {
|
|
127
|
+
name: metadata.name,
|
|
128
|
+
description: metadata.description,
|
|
129
|
+
tools: [{
|
|
130
|
+
name: metadata.name,
|
|
131
|
+
description: metadata.description,
|
|
132
|
+
parameters: z.any(),
|
|
133
|
+
execute: async (params) => {
|
|
134
|
+
// 根据 WASM 导出函数执行逻辑
|
|
135
|
+
if (exports.run) {
|
|
136
|
+
return { success: true, data: exports.run(params) };
|
|
137
|
+
}
|
|
138
|
+
return { success: false, error: 'WASM module has no run() export' };
|
|
139
|
+
}
|
|
140
|
+
}]
|
|
141
|
+
};
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
//# sourceMappingURL=SkillLoader.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SkillLoader.js","sourceRoot":"","sources":["../../../src/core/persistence/SkillLoader.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { ISkillStore, SkillFile, SkillMetadata } from '../../interfaces/index.js';
|
|
2
|
+
/**
|
|
3
|
+
* 前端实现:基于 IndexedDB 的持久化存储
|
|
4
|
+
* 数据库名: JS_AGENT_DB
|
|
5
|
+
* Store 1: skill_metadata (Key: name)
|
|
6
|
+
* Store 2: skill_files (Key: [skillName, filePath])
|
|
7
|
+
*/
|
|
8
|
+
export declare class WebIndexedDbSkillStore implements ISkillStore {
|
|
9
|
+
private dbName;
|
|
10
|
+
private metaStore;
|
|
11
|
+
private fileStore;
|
|
12
|
+
private db;
|
|
13
|
+
constructor();
|
|
14
|
+
private getDB;
|
|
15
|
+
saveSkill(metadata: SkillMetadata, files: SkillFile[]): Promise<void>;
|
|
16
|
+
getSkillFiles(skillName: string): Promise<SkillFile[]>;
|
|
17
|
+
getSkillMetadata(skillName: string): Promise<SkillMetadata | null>;
|
|
18
|
+
listSkills(): Promise<SkillMetadata[]>;
|
|
19
|
+
deleteSkill(skillName: string): Promise<void>;
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=WebIndexedDbSkillStore.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"WebIndexedDbSkillStore.d.ts","sourceRoot":"","sources":["../../../src/core/persistence/WebIndexedDbSkillStore.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAElF;;;;;GAKG;AACH,qBAAa,sBAAuB,YAAW,WAAW;IACxD,OAAO,CAAC,MAAM,CAAiB;IAC/B,OAAO,CAAC,SAAS,CAAoB;IACrC,OAAO,CAAC,SAAS,CAAiB;IAClC,OAAO,CAAC,EAAE,CAA4B;;YAQxB,KAAK;IAyBb,SAAS,CAAC,QAAQ,EAAE,aAAa,EAAE,KAAK,EAAE,SAAS,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC;IAuBrE,aAAa,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC;IAwBtD,gBAAgB,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,GAAG,IAAI,CAAC;IAWlE,UAAU,IAAI,OAAO,CAAC,aAAa,EAAE,CAAC;IAWtC,WAAW,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;CAwBpD"}
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 前端实现:基于 IndexedDB 的持久化存储
|
|
3
|
+
* 数据库名: JS_AGENT_DB
|
|
4
|
+
* Store 1: skill_metadata (Key: name)
|
|
5
|
+
* Store 2: skill_files (Key: [skillName, filePath])
|
|
6
|
+
*/
|
|
7
|
+
export class WebIndexedDbSkillStore {
|
|
8
|
+
dbName = 'JS_AGENT_DB';
|
|
9
|
+
metaStore = 'skill_metadata';
|
|
10
|
+
fileStore = 'skill_files';
|
|
11
|
+
db = null;
|
|
12
|
+
constructor() {
|
|
13
|
+
if (typeof indexedDB === 'undefined') {
|
|
14
|
+
console.warn('IndexedDB is not supported in this environment.');
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
async getDB() {
|
|
18
|
+
if (this.db)
|
|
19
|
+
return this.db;
|
|
20
|
+
return new Promise((resolve, reject) => {
|
|
21
|
+
const request = indexedDB.open(this.dbName, 1);
|
|
22
|
+
request.onupgradeneeded = (event) => {
|
|
23
|
+
const db = event.target.result;
|
|
24
|
+
if (!db.objectStoreNames.contains(this.metaStore)) {
|
|
25
|
+
db.createObjectStore(this.metaStore, { keyPath: 'name' });
|
|
26
|
+
}
|
|
27
|
+
if (!db.objectStoreNames.contains(this.fileStore)) {
|
|
28
|
+
db.createObjectStore(this.fileStore, { keyPath: ['skillName', 'path'] });
|
|
29
|
+
}
|
|
30
|
+
};
|
|
31
|
+
request.onsuccess = (event) => {
|
|
32
|
+
this.db = event.target.result;
|
|
33
|
+
resolve(this.db);
|
|
34
|
+
};
|
|
35
|
+
request.onerror = (event) => reject(event.target.error);
|
|
36
|
+
});
|
|
37
|
+
}
|
|
38
|
+
async saveSkill(metadata, files) {
|
|
39
|
+
const db = await this.getDB();
|
|
40
|
+
const tx = db.transaction([this.metaStore, this.fileStore], 'readwrite');
|
|
41
|
+
// 1. 保存元数据
|
|
42
|
+
tx.objectStore(this.metaStore).put(metadata);
|
|
43
|
+
// 2. 保存文件 (批量写入)
|
|
44
|
+
const fileStore = tx.objectStore(this.fileStore);
|
|
45
|
+
for (const file of files) {
|
|
46
|
+
fileStore.put({
|
|
47
|
+
skillName: metadata.name,
|
|
48
|
+
path: file.path,
|
|
49
|
+
content: file.content
|
|
50
|
+
});
|
|
51
|
+
}
|
|
52
|
+
return new Promise((resolve, reject) => {
|
|
53
|
+
tx.oncomplete = () => resolve();
|
|
54
|
+
tx.onerror = () => reject(tx.error);
|
|
55
|
+
});
|
|
56
|
+
}
|
|
57
|
+
async getSkillFiles(skillName) {
|
|
58
|
+
const db = await this.getDB();
|
|
59
|
+
const tx = db.transaction(this.fileStore, 'readonly');
|
|
60
|
+
const store = tx.objectStore(this.fileStore);
|
|
61
|
+
const index = store.openCursor(IDBKeyRange.bound([skillName, ''], [skillName, '\uffff']));
|
|
62
|
+
const files = [];
|
|
63
|
+
return new Promise((resolve, reject) => {
|
|
64
|
+
index.onsuccess = (event) => {
|
|
65
|
+
const cursor = event.target.result;
|
|
66
|
+
if (cursor) {
|
|
67
|
+
files.push({
|
|
68
|
+
path: cursor.value.path,
|
|
69
|
+
content: cursor.value.content
|
|
70
|
+
});
|
|
71
|
+
cursor.continue();
|
|
72
|
+
}
|
|
73
|
+
else {
|
|
74
|
+
resolve(files);
|
|
75
|
+
}
|
|
76
|
+
};
|
|
77
|
+
index.onerror = () => reject(tx.error);
|
|
78
|
+
});
|
|
79
|
+
}
|
|
80
|
+
async getSkillMetadata(skillName) {
|
|
81
|
+
const db = await this.getDB();
|
|
82
|
+
const tx = db.transaction(this.metaStore, 'readonly');
|
|
83
|
+
const request = tx.objectStore(this.metaStore).get(skillName);
|
|
84
|
+
return new Promise((resolve, reject) => {
|
|
85
|
+
request.onsuccess = () => resolve(request.result || null);
|
|
86
|
+
request.onerror = () => reject(tx.error);
|
|
87
|
+
});
|
|
88
|
+
}
|
|
89
|
+
async listSkills() {
|
|
90
|
+
const db = await this.getDB();
|
|
91
|
+
const tx = db.transaction(this.metaStore, 'readonly');
|
|
92
|
+
const request = tx.objectStore(this.metaStore).getAll();
|
|
93
|
+
return new Promise((resolve, reject) => {
|
|
94
|
+
request.onsuccess = () => resolve(request.result || []);
|
|
95
|
+
request.onerror = () => reject(tx.error);
|
|
96
|
+
});
|
|
97
|
+
}
|
|
98
|
+
async deleteSkill(skillName) {
|
|
99
|
+
const db = await this.getDB();
|
|
100
|
+
const tx = db.transaction([this.metaStore, this.fileStore], 'readwrite');
|
|
101
|
+
// 1. 删除元数据
|
|
102
|
+
tx.objectStore(this.metaStore).delete(skillName);
|
|
103
|
+
// 2. 删除所有关联文件
|
|
104
|
+
const fileStore = tx.objectStore(this.fileStore);
|
|
105
|
+
const index = fileStore.openCursor(IDBKeyRange.bound([skillName, ''], [skillName, '\uffff']));
|
|
106
|
+
index.onsuccess = (event) => {
|
|
107
|
+
const cursor = event.target.result;
|
|
108
|
+
if (cursor) {
|
|
109
|
+
cursor.delete();
|
|
110
|
+
cursor.continue();
|
|
111
|
+
}
|
|
112
|
+
};
|
|
113
|
+
return new Promise((resolve, reject) => {
|
|
114
|
+
tx.oncomplete = () => resolve();
|
|
115
|
+
tx.onerror = () => reject(tx.error);
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
//# sourceMappingURL=WebIndexedDbSkillStore.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"WebIndexedDbSkillStore.js","sourceRoot":"","sources":["../../../src/core/persistence/WebIndexedDbSkillStore.ts"],"names":[],"mappings":"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"}
|