@axiom-lattice/core 2.1.46 → 2.1.47
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +782 -774
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +782 -774
- package/dist/index.mjs.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -4833,516 +4833,241 @@ var createReactAgentSchema = (schema) => {
|
|
|
4833
4833
|
// src/agent_lattice/builders/ReActAgentGraphBuilder.ts
|
|
4834
4834
|
var import_langchain55 = require("langchain");
|
|
4835
4835
|
|
|
4836
|
-
// src/
|
|
4837
|
-
var
|
|
4838
|
-
|
|
4839
|
-
|
|
4840
|
-
|
|
4841
|
-
|
|
4842
|
-
|
|
4843
|
-
|
|
4844
|
-
|
|
4845
|
-
|
|
4846
|
-
|
|
4847
|
-
|
|
4848
|
-
|
|
4849
|
-
|
|
4850
|
-
|
|
4851
|
-
|
|
4852
|
-
|
|
4853
|
-
|
|
4854
|
-
|
|
4855
|
-
|
|
4856
|
-
|
|
4857
|
-
|
|
4858
|
-
|
|
4836
|
+
// src/middlewares/codeEvalMiddleware.ts
|
|
4837
|
+
var import_langchain37 = require("langchain");
|
|
4838
|
+
|
|
4839
|
+
// src/middlewares/contextSchema.ts
|
|
4840
|
+
var import_zod41 = __toESM(require("zod"));
|
|
4841
|
+
var contextSchema = import_zod41.default.object({
|
|
4842
|
+
runConfig: import_zod41.default.any()
|
|
4843
|
+
});
|
|
4844
|
+
|
|
4845
|
+
// src/middlewares/codeEvalMiddleware.ts
|
|
4846
|
+
function createCodeEvalMiddleware(params = { isolatedLevel: "global" }) {
|
|
4847
|
+
const codeEvalTool = createCodeEvalTool({ isolatedLevel: params.isolatedLevel });
|
|
4848
|
+
const codeExecuteFileTool = createCodeExecuteFileTool({ isolatedLevel: params.isolatedLevel });
|
|
4849
|
+
return (0, import_langchain37.createMiddleware)({
|
|
4850
|
+
name: "codeEvalMiddleware",
|
|
4851
|
+
contextSchema,
|
|
4852
|
+
tools: [codeEvalTool, codeExecuteFileTool, getToolClient("convert_to_markdown")]
|
|
4853
|
+
});
|
|
4854
|
+
}
|
|
4855
|
+
|
|
4856
|
+
// src/middlewares/browserMiddleware.ts
|
|
4857
|
+
var import_langchain38 = require("langchain");
|
|
4858
|
+
function createBrowserMiddleware(params = { isolatedLevel: "global" }) {
|
|
4859
|
+
const isolatedLevel = params.isolatedLevel || "global";
|
|
4860
|
+
const tools = [
|
|
4861
|
+
createBrowserNavigateTool({ isolatedLevel }),
|
|
4862
|
+
createBrowserClickTool({ isolatedLevel }),
|
|
4863
|
+
createBrowserGetTextTool({ isolatedLevel }),
|
|
4864
|
+
createBrowserGetMarkdownTool({ isolatedLevel }),
|
|
4865
|
+
createBrowserEvaluateTool({ isolatedLevel }),
|
|
4866
|
+
createBrowserScreenshotTool({ isolatedLevel }),
|
|
4867
|
+
createBrowserScrollTool({ isolatedLevel }),
|
|
4868
|
+
createBrowserFormInputFillTool({ isolatedLevel }),
|
|
4869
|
+
createBrowserSelectTool({ isolatedLevel }),
|
|
4870
|
+
createBrowserHoverTool({ isolatedLevel }),
|
|
4871
|
+
createBrowserGoBackTool({ isolatedLevel }),
|
|
4872
|
+
createBrowserGoForwardTool({ isolatedLevel }),
|
|
4873
|
+
createBrowserNewTabTool({ isolatedLevel }),
|
|
4874
|
+
createBrowserTabListTool({ isolatedLevel }),
|
|
4875
|
+
createBrowserSwitchTabTool({ isolatedLevel }),
|
|
4876
|
+
createBrowserCloseTabTool({ isolatedLevel }),
|
|
4877
|
+
createBrowserCloseTool({ isolatedLevel }),
|
|
4878
|
+
createBrowserPressKeyTool({ isolatedLevel }),
|
|
4879
|
+
createBrowserReadLinksTool({ isolatedLevel }),
|
|
4880
|
+
createBrowserGetClickableElementsTool({ isolatedLevel }),
|
|
4881
|
+
createBrowserGetDownloadListTool({ isolatedLevel }),
|
|
4882
|
+
createBrowserGetInfoTool({ isolatedLevel })
|
|
4883
|
+
];
|
|
4884
|
+
return (0, import_langchain38.createMiddleware)({
|
|
4885
|
+
name: "browserMiddleware",
|
|
4886
|
+
contextSchema,
|
|
4887
|
+
tools
|
|
4888
|
+
});
|
|
4889
|
+
}
|
|
4890
|
+
|
|
4891
|
+
// src/middlewares/sqlMiddleware.ts
|
|
4892
|
+
var import_langchain39 = require("langchain");
|
|
4893
|
+
function createSqlMiddleware(params) {
|
|
4894
|
+
const { databaseKeys, databaseDescriptions } = params;
|
|
4895
|
+
if (!databaseKeys || databaseKeys.length === 0) {
|
|
4896
|
+
return (0, import_langchain39.createMiddleware)({
|
|
4897
|
+
name: "sqlMiddleware",
|
|
4898
|
+
tools: []
|
|
4859
4899
|
});
|
|
4860
|
-
this.baseURL = baseURL;
|
|
4861
|
-
this.maxFileSizeBytes = maxFileSizeMb * 1024 * 1024;
|
|
4862
|
-
this.workingDirectory = workingDirectory;
|
|
4863
|
-
this.homeDir = "/home/gem";
|
|
4864
|
-
}
|
|
4865
|
-
resolvePath(virtualPath) {
|
|
4866
|
-
return path2.join(this.homeDir, this.workingDirectory, virtualPath);
|
|
4867
4900
|
}
|
|
4868
|
-
|
|
4869
|
-
|
|
4870
|
-
|
|
4871
|
-
|
|
4872
|
-
|
|
4873
|
-
|
|
4874
|
-
|
|
4875
|
-
|
|
4876
|
-
|
|
4877
|
-
|
|
4878
|
-
|
|
4901
|
+
const toolParams = {
|
|
4902
|
+
databaseKeys,
|
|
4903
|
+
databaseDescriptions
|
|
4904
|
+
};
|
|
4905
|
+
return (0, import_langchain39.createMiddleware)({
|
|
4906
|
+
name: "sqlMiddleware",
|
|
4907
|
+
contextSchema,
|
|
4908
|
+
tools: [
|
|
4909
|
+
createListTablesSqlTool(toolParams),
|
|
4910
|
+
createInfoSqlTool(toolParams),
|
|
4911
|
+
createQueryCheckerSqlTool(toolParams),
|
|
4912
|
+
createQuerySqlTool(toolParams)
|
|
4913
|
+
]
|
|
4914
|
+
});
|
|
4915
|
+
}
|
|
4916
|
+
|
|
4917
|
+
// src/middlewares/skillMiddleware.ts
|
|
4918
|
+
var import_langchain43 = require("langchain");
|
|
4919
|
+
|
|
4920
|
+
// src/store_lattice/InMemoryThreadStore.ts
|
|
4921
|
+
var InMemoryThreadStore = class {
|
|
4922
|
+
constructor() {
|
|
4923
|
+
// Map<tenantId, Map<assistantId, Map<threadId, Thread>>>
|
|
4924
|
+
this.threads = /* @__PURE__ */ new Map();
|
|
4879
4925
|
}
|
|
4880
4926
|
/**
|
|
4881
|
-
*
|
|
4882
|
-
*
|
|
4883
|
-
* @param dirPath - Virtual directory path (must start with /)
|
|
4884
|
-
* @returns List of FileInfo objects for files and directories directly in the directory.
|
|
4885
|
-
* Directories have a trailing / in their path and is_dir=true.
|
|
4927
|
+
* Get all threads for a specific tenant and assistant
|
|
4886
4928
|
*/
|
|
4887
|
-
async
|
|
4888
|
-
|
|
4889
|
-
|
|
4890
|
-
|
|
4891
|
-
|
|
4892
|
-
|
|
4893
|
-
|
|
4894
|
-
max_depth: 0,
|
|
4895
|
-
include_size: false,
|
|
4896
|
-
include_permissions: false,
|
|
4897
|
-
sort_by: "name",
|
|
4898
|
-
sort_desc: false
|
|
4899
|
-
});
|
|
4900
|
-
if (!result.ok) {
|
|
4901
|
-
throw result.error;
|
|
4902
|
-
}
|
|
4903
|
-
const files = result.body?.data?.files?.map((file) => ({
|
|
4904
|
-
path: this.toVirtualPath(file.path),
|
|
4905
|
-
is_dir: file.is_directory,
|
|
4906
|
-
size: file.size,
|
|
4907
|
-
modified_at: file.modified_time
|
|
4908
|
-
})) || [];
|
|
4909
|
-
return files;
|
|
4910
|
-
} catch (e) {
|
|
4911
|
-
console.error(`Error listing files in ${dirPath}:`, e);
|
|
4929
|
+
async getThreadsByAssistantId(tenantId, assistantId, metadataFilter) {
|
|
4930
|
+
const tenantThreads = this.threads.get(tenantId);
|
|
4931
|
+
if (!tenantThreads) {
|
|
4932
|
+
return [];
|
|
4933
|
+
}
|
|
4934
|
+
const assistantThreads = tenantThreads.get(assistantId);
|
|
4935
|
+
if (!assistantThreads) {
|
|
4912
4936
|
return [];
|
|
4913
4937
|
}
|
|
4938
|
+
let threads = Array.from(assistantThreads.values());
|
|
4939
|
+
if (metadataFilter && Object.keys(metadataFilter).length > 0) {
|
|
4940
|
+
threads = threads.filter(
|
|
4941
|
+
(thread) => Object.entries(metadataFilter).every(
|
|
4942
|
+
([key, value]) => thread.metadata?.[key] === value
|
|
4943
|
+
)
|
|
4944
|
+
);
|
|
4945
|
+
}
|
|
4946
|
+
return threads;
|
|
4914
4947
|
}
|
|
4915
4948
|
/**
|
|
4916
|
-
*
|
|
4917
|
-
*
|
|
4918
|
-
* @param filePath - Virtual file path (must start with /)
|
|
4919
|
-
* @param offset - Line offset to start reading from (0-indexed)
|
|
4920
|
-
* @param limit - Maximum number of lines to read
|
|
4921
|
-
* @returns Formatted file content with line numbers, or error message
|
|
4949
|
+
* Get a thread by ID for a specific tenant
|
|
4922
4950
|
*/
|
|
4923
|
-
async
|
|
4924
|
-
|
|
4925
|
-
|
|
4926
|
-
|
|
4927
|
-
|
|
4928
|
-
|
|
4929
|
-
|
|
4930
|
-
|
|
4931
|
-
|
|
4932
|
-
if (!result.ok) {
|
|
4933
|
-
throw result.error;
|
|
4951
|
+
async getThreadById(tenantId, threadId) {
|
|
4952
|
+
const tenantThreads = this.threads.get(tenantId);
|
|
4953
|
+
if (!tenantThreads) {
|
|
4954
|
+
return void 0;
|
|
4955
|
+
}
|
|
4956
|
+
for (const assistantThreads of tenantThreads.values()) {
|
|
4957
|
+
const thread = assistantThreads.get(threadId);
|
|
4958
|
+
if (thread) {
|
|
4959
|
+
return thread;
|
|
4934
4960
|
}
|
|
4935
|
-
content = result.body?.data?.content || "";
|
|
4936
|
-
return content;
|
|
4937
|
-
} catch (e) {
|
|
4938
|
-
return `Error: File '${filePath}' not found`;
|
|
4939
4961
|
}
|
|
4962
|
+
return void 0;
|
|
4940
4963
|
}
|
|
4941
4964
|
/**
|
|
4942
|
-
*
|
|
4943
|
-
*
|
|
4944
|
-
* @param filePath - Virtual file path (must start with /)
|
|
4945
|
-
* @returns Raw file content as FileData
|
|
4965
|
+
* Create a new thread for a tenant and assistant
|
|
4946
4966
|
*/
|
|
4947
|
-
async
|
|
4948
|
-
|
|
4949
|
-
|
|
4950
|
-
|
|
4951
|
-
|
|
4952
|
-
|
|
4953
|
-
|
|
4954
|
-
|
|
4955
|
-
|
|
4956
|
-
|
|
4967
|
+
async createThread(tenantId, assistantId, threadId, data) {
|
|
4968
|
+
const now = /* @__PURE__ */ new Date();
|
|
4969
|
+
const thread = {
|
|
4970
|
+
id: threadId,
|
|
4971
|
+
tenantId,
|
|
4972
|
+
assistantId,
|
|
4973
|
+
metadata: data.metadata || {},
|
|
4974
|
+
createdAt: now,
|
|
4975
|
+
updatedAt: now
|
|
4976
|
+
};
|
|
4977
|
+
if (!this.threads.has(tenantId)) {
|
|
4978
|
+
this.threads.set(tenantId, /* @__PURE__ */ new Map());
|
|
4979
|
+
}
|
|
4980
|
+
const tenantThreads = this.threads.get(tenantId);
|
|
4981
|
+
if (!tenantThreads.has(assistantId)) {
|
|
4982
|
+
tenantThreads.set(assistantId, /* @__PURE__ */ new Map());
|
|
4957
4983
|
}
|
|
4984
|
+
const assistantThreads = tenantThreads.get(assistantId);
|
|
4985
|
+
assistantThreads.set(threadId, thread);
|
|
4986
|
+
return thread;
|
|
4958
4987
|
}
|
|
4959
4988
|
/**
|
|
4960
|
-
*
|
|
4961
|
-
* Returns WriteResult. External storage sets filesUpdate=null.
|
|
4962
|
-
*
|
|
4963
|
-
* @param filePath - Virtual file path (must start with /)
|
|
4964
|
-
* @param content - File content as string
|
|
4965
|
-
* @returns WriteResult with error populated on failure
|
|
4989
|
+
* Update an existing thread
|
|
4966
4990
|
*/
|
|
4967
|
-
async
|
|
4968
|
-
|
|
4969
|
-
|
|
4970
|
-
|
|
4971
|
-
|
|
4972
|
-
|
|
4973
|
-
|
|
4974
|
-
|
|
4975
|
-
|
|
4976
|
-
|
|
4977
|
-
|
|
4978
|
-
|
|
4979
|
-
|
|
4991
|
+
async updateThread(tenantId, threadId, updates) {
|
|
4992
|
+
const tenantThreads = this.threads.get(tenantId);
|
|
4993
|
+
if (!tenantThreads) {
|
|
4994
|
+
return null;
|
|
4995
|
+
}
|
|
4996
|
+
for (const assistantThreads of tenantThreads.values()) {
|
|
4997
|
+
const existing = assistantThreads.get(threadId);
|
|
4998
|
+
if (existing) {
|
|
4999
|
+
const updated = {
|
|
5000
|
+
...existing,
|
|
5001
|
+
metadata: {
|
|
5002
|
+
...existing.metadata,
|
|
5003
|
+
...updates.metadata || {}
|
|
5004
|
+
},
|
|
5005
|
+
updatedAt: /* @__PURE__ */ new Date()
|
|
5006
|
+
};
|
|
5007
|
+
assistantThreads.set(threadId, updated);
|
|
5008
|
+
return updated;
|
|
4980
5009
|
}
|
|
4981
|
-
return {
|
|
4982
|
-
path: filePath,
|
|
4983
|
-
filesUpdate: {
|
|
4984
|
-
[filePath]: {
|
|
4985
|
-
content: content.split("\n"),
|
|
4986
|
-
created_at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
4987
|
-
modified_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
4988
|
-
}
|
|
4989
|
-
}
|
|
4990
|
-
};
|
|
4991
|
-
} catch (e) {
|
|
4992
|
-
throw new Error(`Error writing file '${filePath}': ${e.message}`);
|
|
4993
5010
|
}
|
|
5011
|
+
return null;
|
|
4994
5012
|
}
|
|
4995
5013
|
/**
|
|
4996
|
-
*
|
|
4997
|
-
* Returns EditResult. External storage sets filesUpdate=null.
|
|
4998
|
-
*
|
|
4999
|
-
* @param filePath - Virtual file path (must start with /)
|
|
5000
|
-
* @param oldString - String to find and replace
|
|
5001
|
-
* @param newString - Replacement string
|
|
5002
|
-
* @param replaceAll - If true, replace all occurrences (default: false)
|
|
5003
|
-
* @returns EditResult with error, path, filesUpdate, and occurrences
|
|
5014
|
+
* Delete a thread by ID
|
|
5004
5015
|
*/
|
|
5005
|
-
async
|
|
5006
|
-
|
|
5007
|
-
|
|
5008
|
-
|
|
5009
|
-
|
|
5010
|
-
|
|
5011
|
-
|
|
5012
|
-
|
|
5013
|
-
replace_mode: replaceAll ? "ALL" : "FIRST"
|
|
5014
|
-
});
|
|
5015
|
-
if (!result.ok) {
|
|
5016
|
-
throw result.error;
|
|
5016
|
+
async deleteThread(tenantId, threadId) {
|
|
5017
|
+
const tenantThreads = this.threads.get(tenantId);
|
|
5018
|
+
if (!tenantThreads) {
|
|
5019
|
+
return false;
|
|
5020
|
+
}
|
|
5021
|
+
for (const assistantThreads of tenantThreads.values()) {
|
|
5022
|
+
if (assistantThreads.has(threadId)) {
|
|
5023
|
+
return assistantThreads.delete(threadId);
|
|
5017
5024
|
}
|
|
5018
|
-
return {
|
|
5019
|
-
path: filePath,
|
|
5020
|
-
filesUpdate: null
|
|
5021
|
-
};
|
|
5022
|
-
} catch (e) {
|
|
5023
|
-
throw new Error(`Error editing file '${filePath}': ${e.message}`);
|
|
5024
5025
|
}
|
|
5026
|
+
return false;
|
|
5025
5027
|
}
|
|
5026
5028
|
/**
|
|
5027
|
-
*
|
|
5028
|
-
*
|
|
5029
|
-
* Searches file contents for a regex pattern within the sandbox.
|
|
5030
|
-
*
|
|
5031
|
-
* @param pattern - Regex pattern to search for
|
|
5032
|
-
* @param searchPath - Base path to search from (default: "/")
|
|
5033
|
-
* @param glob - Optional glob pattern to filter files (e.g., "*.py")
|
|
5034
|
-
* @returns List of GrepMatch objects or error string for invalid regex
|
|
5029
|
+
* Check if thread exists
|
|
5035
5030
|
*/
|
|
5036
|
-
async
|
|
5037
|
-
|
|
5038
|
-
|
|
5039
|
-
|
|
5040
|
-
path: baseFull,
|
|
5041
|
-
glob: glob || "**/*"
|
|
5042
|
-
});
|
|
5043
|
-
if (!result.ok) {
|
|
5044
|
-
throw result.error;
|
|
5031
|
+
async hasThread(tenantId, threadId) {
|
|
5032
|
+
const tenantThreads = this.threads.get(tenantId);
|
|
5033
|
+
if (!tenantThreads) {
|
|
5034
|
+
return false;
|
|
5045
5035
|
}
|
|
5046
|
-
const
|
|
5047
|
-
|
|
5048
|
-
|
|
5049
|
-
const fileData = await this.sandbox.file.searchInFile({
|
|
5050
|
-
file: absolutePath,
|
|
5051
|
-
regex: pattern
|
|
5052
|
-
});
|
|
5053
|
-
if (!fileData.ok) {
|
|
5054
|
-
continue;
|
|
5036
|
+
for (const assistantThreads of tenantThreads.values()) {
|
|
5037
|
+
if (assistantThreads.has(threadId)) {
|
|
5038
|
+
return true;
|
|
5055
5039
|
}
|
|
5056
|
-
const matchesData = fileData.body?.data?.matches || [];
|
|
5057
|
-
const matchLines = fileData.body?.data?.line_numbers || [];
|
|
5058
|
-
matchesData.forEach((match, index) => {
|
|
5059
|
-
matches.push({
|
|
5060
|
-
path: this.toVirtualPath(absolutePath),
|
|
5061
|
-
line: matchLines[index],
|
|
5062
|
-
text: match
|
|
5063
|
-
});
|
|
5064
|
-
});
|
|
5065
5040
|
}
|
|
5066
|
-
return
|
|
5041
|
+
return false;
|
|
5067
5042
|
}
|
|
5068
5043
|
/**
|
|
5069
|
-
*
|
|
5070
|
-
*
|
|
5071
|
-
* @param pattern - Glob pattern (e.g., `*.py`, `**\/*.ts`)
|
|
5072
|
-
* @param searchPath - Base path to search from (default: "/")
|
|
5073
|
-
* @returns List of FileInfo objects matching the pattern
|
|
5044
|
+
* Clear all threads for a tenant (useful for testing)
|
|
5074
5045
|
*/
|
|
5075
|
-
|
|
5076
|
-
if (
|
|
5077
|
-
|
|
5078
|
-
}
|
|
5079
|
-
|
|
5080
|
-
const result = await this.sandbox.file.findFiles({
|
|
5081
|
-
path: resolvedSearchPath,
|
|
5082
|
-
glob: pattern || "**/*"
|
|
5083
|
-
});
|
|
5084
|
-
if (!result.ok) {
|
|
5085
|
-
throw result.error;
|
|
5046
|
+
clear(tenantId) {
|
|
5047
|
+
if (tenantId) {
|
|
5048
|
+
this.threads.delete(tenantId);
|
|
5049
|
+
} else {
|
|
5050
|
+
this.threads.clear();
|
|
5086
5051
|
}
|
|
5087
|
-
|
|
5088
|
-
|
|
5089
|
-
|
|
5090
|
-
|
|
5091
|
-
|
|
5092
|
-
|
|
5093
|
-
|
|
5094
|
-
|
|
5095
|
-
|
|
5096
|
-
});
|
|
5097
|
-
if (!fileInfo.ok) {
|
|
5098
|
-
continue;
|
|
5052
|
+
}
|
|
5053
|
+
/**
|
|
5054
|
+
* Get all threads for all assistants (useful for debugging)
|
|
5055
|
+
*/
|
|
5056
|
+
getAllThreads() {
|
|
5057
|
+
const allThreads = [];
|
|
5058
|
+
for (const tenantThreads of this.threads.values()) {
|
|
5059
|
+
for (const assistantThreads of tenantThreads.values()) {
|
|
5060
|
+
allThreads.push(...Array.from(assistantThreads.values()));
|
|
5099
5061
|
}
|
|
5100
|
-
results.push({
|
|
5101
|
-
path: this.toVirtualPath(filePath),
|
|
5102
|
-
is_dir: false,
|
|
5103
|
-
size: fileInfo.body?.data?.files?.[0]?.size,
|
|
5104
|
-
modified_at: fileInfo.body?.data?.files?.[0]?.modified_time
|
|
5105
|
-
});
|
|
5106
5062
|
}
|
|
5107
|
-
return
|
|
5063
|
+
return allThreads;
|
|
5108
5064
|
}
|
|
5109
5065
|
};
|
|
5110
5066
|
|
|
5111
|
-
// src/
|
|
5112
|
-
var
|
|
5113
|
-
|
|
5114
|
-
// src/middlewares/contextSchema.ts
|
|
5115
|
-
var import_zod41 = __toESM(require("zod"));
|
|
5116
|
-
var contextSchema = import_zod41.default.object({
|
|
5117
|
-
runConfig: import_zod41.default.any()
|
|
5118
|
-
});
|
|
5119
|
-
|
|
5120
|
-
// src/middlewares/codeEvalMiddleware.ts
|
|
5121
|
-
function createCodeEvalMiddleware(params = { isolatedLevel: "global" }) {
|
|
5122
|
-
const codeEvalTool = createCodeEvalTool({ isolatedLevel: params.isolatedLevel });
|
|
5123
|
-
const codeExecuteFileTool = createCodeExecuteFileTool({ isolatedLevel: params.isolatedLevel });
|
|
5124
|
-
return (0, import_langchain37.createMiddleware)({
|
|
5125
|
-
name: "codeEvalMiddleware",
|
|
5126
|
-
contextSchema,
|
|
5127
|
-
tools: [codeEvalTool, codeExecuteFileTool, getToolClient("convert_to_markdown")]
|
|
5128
|
-
});
|
|
5129
|
-
}
|
|
5130
|
-
|
|
5131
|
-
// src/middlewares/browserMiddleware.ts
|
|
5132
|
-
var import_langchain38 = require("langchain");
|
|
5133
|
-
function createBrowserMiddleware(params = { isolatedLevel: "global" }) {
|
|
5134
|
-
const isolatedLevel = params.isolatedLevel || "global";
|
|
5135
|
-
const tools = [
|
|
5136
|
-
createBrowserNavigateTool({ isolatedLevel }),
|
|
5137
|
-
createBrowserClickTool({ isolatedLevel }),
|
|
5138
|
-
createBrowserGetTextTool({ isolatedLevel }),
|
|
5139
|
-
createBrowserGetMarkdownTool({ isolatedLevel }),
|
|
5140
|
-
createBrowserEvaluateTool({ isolatedLevel }),
|
|
5141
|
-
createBrowserScreenshotTool({ isolatedLevel }),
|
|
5142
|
-
createBrowserScrollTool({ isolatedLevel }),
|
|
5143
|
-
createBrowserFormInputFillTool({ isolatedLevel }),
|
|
5144
|
-
createBrowserSelectTool({ isolatedLevel }),
|
|
5145
|
-
createBrowserHoverTool({ isolatedLevel }),
|
|
5146
|
-
createBrowserGoBackTool({ isolatedLevel }),
|
|
5147
|
-
createBrowserGoForwardTool({ isolatedLevel }),
|
|
5148
|
-
createBrowserNewTabTool({ isolatedLevel }),
|
|
5149
|
-
createBrowserTabListTool({ isolatedLevel }),
|
|
5150
|
-
createBrowserSwitchTabTool({ isolatedLevel }),
|
|
5151
|
-
createBrowserCloseTabTool({ isolatedLevel }),
|
|
5152
|
-
createBrowserCloseTool({ isolatedLevel }),
|
|
5153
|
-
createBrowserPressKeyTool({ isolatedLevel }),
|
|
5154
|
-
createBrowserReadLinksTool({ isolatedLevel }),
|
|
5155
|
-
createBrowserGetClickableElementsTool({ isolatedLevel }),
|
|
5156
|
-
createBrowserGetDownloadListTool({ isolatedLevel }),
|
|
5157
|
-
createBrowserGetInfoTool({ isolatedLevel })
|
|
5158
|
-
];
|
|
5159
|
-
return (0, import_langchain38.createMiddleware)({
|
|
5160
|
-
name: "browserMiddleware",
|
|
5161
|
-
contextSchema,
|
|
5162
|
-
tools
|
|
5163
|
-
});
|
|
5164
|
-
}
|
|
5165
|
-
|
|
5166
|
-
// src/middlewares/sqlMiddleware.ts
|
|
5167
|
-
var import_langchain39 = require("langchain");
|
|
5168
|
-
function createSqlMiddleware(params) {
|
|
5169
|
-
const { databaseKeys, databaseDescriptions } = params;
|
|
5170
|
-
if (!databaseKeys || databaseKeys.length === 0) {
|
|
5171
|
-
return (0, import_langchain39.createMiddleware)({
|
|
5172
|
-
name: "sqlMiddleware",
|
|
5173
|
-
tools: []
|
|
5174
|
-
});
|
|
5175
|
-
}
|
|
5176
|
-
const toolParams = {
|
|
5177
|
-
databaseKeys,
|
|
5178
|
-
databaseDescriptions
|
|
5179
|
-
};
|
|
5180
|
-
return (0, import_langchain39.createMiddleware)({
|
|
5181
|
-
name: "sqlMiddleware",
|
|
5182
|
-
contextSchema,
|
|
5183
|
-
tools: [
|
|
5184
|
-
createListTablesSqlTool(toolParams),
|
|
5185
|
-
createInfoSqlTool(toolParams),
|
|
5186
|
-
createQueryCheckerSqlTool(toolParams),
|
|
5187
|
-
createQuerySqlTool(toolParams)
|
|
5188
|
-
]
|
|
5189
|
-
});
|
|
5190
|
-
}
|
|
5191
|
-
|
|
5192
|
-
// src/middlewares/skillMiddleware.ts
|
|
5193
|
-
var import_langchain43 = require("langchain");
|
|
5194
|
-
|
|
5195
|
-
// src/store_lattice/InMemoryThreadStore.ts
|
|
5196
|
-
var InMemoryThreadStore = class {
|
|
5067
|
+
// src/store_lattice/InMemoryAssistantStore.ts
|
|
5068
|
+
var InMemoryAssistantStore = class {
|
|
5197
5069
|
constructor() {
|
|
5198
|
-
|
|
5199
|
-
this.threads = /* @__PURE__ */ new Map();
|
|
5200
|
-
}
|
|
5201
|
-
/**
|
|
5202
|
-
* Get all threads for a specific tenant and assistant
|
|
5203
|
-
*/
|
|
5204
|
-
async getThreadsByAssistantId(tenantId, assistantId, metadataFilter) {
|
|
5205
|
-
const tenantThreads = this.threads.get(tenantId);
|
|
5206
|
-
if (!tenantThreads) {
|
|
5207
|
-
return [];
|
|
5208
|
-
}
|
|
5209
|
-
const assistantThreads = tenantThreads.get(assistantId);
|
|
5210
|
-
if (!assistantThreads) {
|
|
5211
|
-
return [];
|
|
5212
|
-
}
|
|
5213
|
-
let threads = Array.from(assistantThreads.values());
|
|
5214
|
-
if (metadataFilter && Object.keys(metadataFilter).length > 0) {
|
|
5215
|
-
threads = threads.filter(
|
|
5216
|
-
(thread) => Object.entries(metadataFilter).every(
|
|
5217
|
-
([key, value]) => thread.metadata?.[key] === value
|
|
5218
|
-
)
|
|
5219
|
-
);
|
|
5220
|
-
}
|
|
5221
|
-
return threads;
|
|
5222
|
-
}
|
|
5223
|
-
/**
|
|
5224
|
-
* Get a thread by ID for a specific tenant
|
|
5225
|
-
*/
|
|
5226
|
-
async getThreadById(tenantId, threadId) {
|
|
5227
|
-
const tenantThreads = this.threads.get(tenantId);
|
|
5228
|
-
if (!tenantThreads) {
|
|
5229
|
-
return void 0;
|
|
5230
|
-
}
|
|
5231
|
-
for (const assistantThreads of tenantThreads.values()) {
|
|
5232
|
-
const thread = assistantThreads.get(threadId);
|
|
5233
|
-
if (thread) {
|
|
5234
|
-
return thread;
|
|
5235
|
-
}
|
|
5236
|
-
}
|
|
5237
|
-
return void 0;
|
|
5238
|
-
}
|
|
5239
|
-
/**
|
|
5240
|
-
* Create a new thread for a tenant and assistant
|
|
5241
|
-
*/
|
|
5242
|
-
async createThread(tenantId, assistantId, threadId, data) {
|
|
5243
|
-
const now = /* @__PURE__ */ new Date();
|
|
5244
|
-
const thread = {
|
|
5245
|
-
id: threadId,
|
|
5246
|
-
tenantId,
|
|
5247
|
-
assistantId,
|
|
5248
|
-
metadata: data.metadata || {},
|
|
5249
|
-
createdAt: now,
|
|
5250
|
-
updatedAt: now
|
|
5251
|
-
};
|
|
5252
|
-
if (!this.threads.has(tenantId)) {
|
|
5253
|
-
this.threads.set(tenantId, /* @__PURE__ */ new Map());
|
|
5254
|
-
}
|
|
5255
|
-
const tenantThreads = this.threads.get(tenantId);
|
|
5256
|
-
if (!tenantThreads.has(assistantId)) {
|
|
5257
|
-
tenantThreads.set(assistantId, /* @__PURE__ */ new Map());
|
|
5258
|
-
}
|
|
5259
|
-
const assistantThreads = tenantThreads.get(assistantId);
|
|
5260
|
-
assistantThreads.set(threadId, thread);
|
|
5261
|
-
return thread;
|
|
5262
|
-
}
|
|
5263
|
-
/**
|
|
5264
|
-
* Update an existing thread
|
|
5265
|
-
*/
|
|
5266
|
-
async updateThread(tenantId, threadId, updates) {
|
|
5267
|
-
const tenantThreads = this.threads.get(tenantId);
|
|
5268
|
-
if (!tenantThreads) {
|
|
5269
|
-
return null;
|
|
5270
|
-
}
|
|
5271
|
-
for (const assistantThreads of tenantThreads.values()) {
|
|
5272
|
-
const existing = assistantThreads.get(threadId);
|
|
5273
|
-
if (existing) {
|
|
5274
|
-
const updated = {
|
|
5275
|
-
...existing,
|
|
5276
|
-
metadata: {
|
|
5277
|
-
...existing.metadata,
|
|
5278
|
-
...updates.metadata || {}
|
|
5279
|
-
},
|
|
5280
|
-
updatedAt: /* @__PURE__ */ new Date()
|
|
5281
|
-
};
|
|
5282
|
-
assistantThreads.set(threadId, updated);
|
|
5283
|
-
return updated;
|
|
5284
|
-
}
|
|
5285
|
-
}
|
|
5286
|
-
return null;
|
|
5287
|
-
}
|
|
5288
|
-
/**
|
|
5289
|
-
* Delete a thread by ID
|
|
5290
|
-
*/
|
|
5291
|
-
async deleteThread(tenantId, threadId) {
|
|
5292
|
-
const tenantThreads = this.threads.get(tenantId);
|
|
5293
|
-
if (!tenantThreads) {
|
|
5294
|
-
return false;
|
|
5295
|
-
}
|
|
5296
|
-
for (const assistantThreads of tenantThreads.values()) {
|
|
5297
|
-
if (assistantThreads.has(threadId)) {
|
|
5298
|
-
return assistantThreads.delete(threadId);
|
|
5299
|
-
}
|
|
5300
|
-
}
|
|
5301
|
-
return false;
|
|
5302
|
-
}
|
|
5303
|
-
/**
|
|
5304
|
-
* Check if thread exists
|
|
5305
|
-
*/
|
|
5306
|
-
async hasThread(tenantId, threadId) {
|
|
5307
|
-
const tenantThreads = this.threads.get(tenantId);
|
|
5308
|
-
if (!tenantThreads) {
|
|
5309
|
-
return false;
|
|
5310
|
-
}
|
|
5311
|
-
for (const assistantThreads of tenantThreads.values()) {
|
|
5312
|
-
if (assistantThreads.has(threadId)) {
|
|
5313
|
-
return true;
|
|
5314
|
-
}
|
|
5315
|
-
}
|
|
5316
|
-
return false;
|
|
5317
|
-
}
|
|
5318
|
-
/**
|
|
5319
|
-
* Clear all threads for a tenant (useful for testing)
|
|
5320
|
-
*/
|
|
5321
|
-
clear(tenantId) {
|
|
5322
|
-
if (tenantId) {
|
|
5323
|
-
this.threads.delete(tenantId);
|
|
5324
|
-
} else {
|
|
5325
|
-
this.threads.clear();
|
|
5326
|
-
}
|
|
5327
|
-
}
|
|
5328
|
-
/**
|
|
5329
|
-
* Get all threads for all assistants (useful for debugging)
|
|
5330
|
-
*/
|
|
5331
|
-
getAllThreads() {
|
|
5332
|
-
const allThreads = [];
|
|
5333
|
-
for (const tenantThreads of this.threads.values()) {
|
|
5334
|
-
for (const assistantThreads of tenantThreads.values()) {
|
|
5335
|
-
allThreads.push(...Array.from(assistantThreads.values()));
|
|
5336
|
-
}
|
|
5337
|
-
}
|
|
5338
|
-
return allThreads;
|
|
5339
|
-
}
|
|
5340
|
-
};
|
|
5341
|
-
|
|
5342
|
-
// src/store_lattice/InMemoryAssistantStore.ts
|
|
5343
|
-
var InMemoryAssistantStore = class {
|
|
5344
|
-
constructor() {
|
|
5345
|
-
this.assistants = /* @__PURE__ */ new Map();
|
|
5070
|
+
this.assistants = /* @__PURE__ */ new Map();
|
|
5346
5071
|
}
|
|
5347
5072
|
/**
|
|
5348
5073
|
* Get all assistants for a tenant
|
|
@@ -5434,7 +5159,7 @@ var InMemoryAssistantStore = class {
|
|
|
5434
5159
|
|
|
5435
5160
|
// src/store_lattice/FileSystemSkillStore.ts
|
|
5436
5161
|
var fs = __toESM(require("fs/promises"));
|
|
5437
|
-
var
|
|
5162
|
+
var path2 = __toESM(require("path"));
|
|
5438
5163
|
|
|
5439
5164
|
// src/skill_lattice/skillNameValidator.ts
|
|
5440
5165
|
var SKILL_NAME_REGEX = /^[a-z0-9]+(-[a-z0-9]+)*$/;
|
|
@@ -5607,10 +5332,10 @@ var FileSystemSkillStore = class {
|
|
|
5607
5332
|
constructor(options = {}) {
|
|
5608
5333
|
const defaultPath = "lattice_store/skills";
|
|
5609
5334
|
const providedPath = options.rootDir || defaultPath;
|
|
5610
|
-
if (
|
|
5335
|
+
if (path2.isAbsolute(providedPath)) {
|
|
5611
5336
|
this.rootDir = providedPath;
|
|
5612
5337
|
} else {
|
|
5613
|
-
this.rootDir =
|
|
5338
|
+
this.rootDir = path2.resolve(process.cwd(), providedPath);
|
|
5614
5339
|
}
|
|
5615
5340
|
this.ensureDirectoryExists().catch((error) => {
|
|
5616
5341
|
console.error("Failed to initialize FileSystemSkillStore:", error);
|
|
@@ -5634,14 +5359,14 @@ var FileSystemSkillStore = class {
|
|
|
5634
5359
|
if (name.includes("..") || name.includes("/") || name.includes("\\")) {
|
|
5635
5360
|
throw new Error(`Invalid skill name: ${name} (contains invalid characters)`);
|
|
5636
5361
|
}
|
|
5637
|
-
return
|
|
5362
|
+
return path2.join(this.rootDir, name);
|
|
5638
5363
|
}
|
|
5639
5364
|
/**
|
|
5640
5365
|
* Get file path for a skill name
|
|
5641
5366
|
* File is always named SKILL.md inside the name directory
|
|
5642
5367
|
*/
|
|
5643
5368
|
getSkillFilePath(name) {
|
|
5644
|
-
return
|
|
5369
|
+
return path2.join(this.getSkillDirectoryPath(name), "SKILL.md");
|
|
5645
5370
|
}
|
|
5646
5371
|
/**
|
|
5647
5372
|
* Read skill from file
|
|
@@ -5928,14 +5653,14 @@ ${body}` : `${frontmatter}
|
|
|
5928
5653
|
*/
|
|
5929
5654
|
async listSkillResources(_tenantId, skillName) {
|
|
5930
5655
|
const skillDir = this.getSkillDirectoryPath(skillName);
|
|
5931
|
-
const resourcesDir =
|
|
5656
|
+
const resourcesDir = path2.join(skillDir, "resources");
|
|
5932
5657
|
try {
|
|
5933
5658
|
const entries = await fs.readdir(resourcesDir, { withFileTypes: true, recursive: true });
|
|
5934
5659
|
const resources = [];
|
|
5935
5660
|
for (const entry of entries) {
|
|
5936
5661
|
if (!entry.isDirectory()) {
|
|
5937
|
-
const fullPath =
|
|
5938
|
-
const relativePath =
|
|
5662
|
+
const fullPath = path2.join(entry.path, entry.name);
|
|
5663
|
+
const relativePath = path2.relative(resourcesDir, fullPath);
|
|
5939
5664
|
resources.push(relativePath.replace(/\\/g, "/"));
|
|
5940
5665
|
}
|
|
5941
5666
|
}
|
|
@@ -5956,10 +5681,10 @@ ${body}` : `${frontmatter}
|
|
|
5956
5681
|
*/
|
|
5957
5682
|
async loadSkillResource(_tenantId, skillName, resourcePath) {
|
|
5958
5683
|
const skillDir = this.getSkillDirectoryPath(skillName);
|
|
5959
|
-
const resourcesDir =
|
|
5960
|
-
const fullPath =
|
|
5961
|
-
const resolvedPath =
|
|
5962
|
-
const resolvedResourcesDir =
|
|
5684
|
+
const resourcesDir = path2.join(skillDir, "resources");
|
|
5685
|
+
const fullPath = path2.join(resourcesDir, resourcePath);
|
|
5686
|
+
const resolvedPath = path2.resolve(fullPath);
|
|
5687
|
+
const resolvedResourcesDir = path2.resolve(resourcesDir);
|
|
5963
5688
|
if (!resolvedPath.startsWith(resolvedResourcesDir)) {
|
|
5964
5689
|
throw new Error(`Invalid resource path: ${resourcePath}`);
|
|
5965
5690
|
}
|
|
@@ -9495,22 +9220,19 @@ var import_langchain52 = require("langchain");
|
|
|
9495
9220
|
|
|
9496
9221
|
// src/deep_agent_new/middleware/AGENTS_MD.ts
|
|
9497
9222
|
var AGENTS_MD = `
|
|
9498
|
-
# AGENTS.md - Your Workspace
|
|
9499
|
-
|
|
9500
|
-
This folder is home. Treat it that way.
|
|
9501
9223
|
|
|
9502
9224
|
## First Run
|
|
9503
9225
|
|
|
9504
|
-
If
|
|
9226
|
+
If \`/agent/BOOTSTRAP.md\` exists, that's your birth certificate. Follow it, figure out who you are, then delete it. You won't need it again.
|
|
9505
9227
|
|
|
9506
9228
|
## Every Session
|
|
9507
9229
|
|
|
9508
9230
|
Before doing anything else:
|
|
9509
9231
|
|
|
9510
|
-
1. Read
|
|
9511
|
-
2. Read
|
|
9232
|
+
1. Read \`/agent/SOUL.md\` \u2014 this is who you are
|
|
9233
|
+
2. Read \`/agent/USER.md\` \u2014 this is who you're helping
|
|
9512
9234
|
3. Read \`memory/YYYY-MM-DD.md\` (today + yesterday) for recent context
|
|
9513
|
-
4. **If in MAIN SESSION** (direct chat with your human): Also read
|
|
9235
|
+
4. **If in MAIN SESSION** (direct chat with your human): Also read \`/agent/MEMORY.md\`
|
|
9514
9236
|
|
|
9515
9237
|
Don't ask permission. Just do it.
|
|
9516
9238
|
|
|
@@ -9518,17 +9240,18 @@ Don't ask permission. Just do it.
|
|
|
9518
9240
|
|
|
9519
9241
|
You wake up fresh each session. These files are your continuity:
|
|
9520
9242
|
|
|
9521
|
-
- **
|
|
9522
|
-
- **
|
|
9243
|
+
- **agent Long-term:** \`/agent/MEMORY.md\` \u2014 your curated memories, like a human's long-term memory
|
|
9244
|
+
- **Project Memory**: \`/PROJECT.md\` - Loaded from project root if available - Project-specific instructions
|
|
9245
|
+
- **Daily Project notes:** \`/daily/YYYY-MM-DD.md\` (create \`daily/\` if needed) \u2014 raw logs of what happened
|
|
9523
9246
|
|
|
9524
9247
|
Capture what matters. Decisions, context, things to remember. Skip the secrets unless asked to keep them.
|
|
9525
9248
|
|
|
9526
|
-
### \u{1F9E0} MEMORY.md - Your Long-Term Memory
|
|
9249
|
+
### \u{1F9E0} /agent/MEMORY.md - Your Long-Term Memory
|
|
9527
9250
|
|
|
9528
9251
|
- **ONLY load in main session** (direct chats with your human)
|
|
9529
9252
|
- **DO NOT load in shared contexts** (Discord, group chats, sessions with other people)
|
|
9530
9253
|
- This is for **security** \u2014 contains personal context that shouldn't leak to strangers
|
|
9531
|
-
- You can **read, edit, and update** MEMORY.md freely in main sessions
|
|
9254
|
+
- You can **read, edit, and update** /agent/MEMORY.md freely in main sessions
|
|
9532
9255
|
- Write significant events, thoughts, decisions, opinions, lessons learned
|
|
9533
9256
|
- This is your curated memory \u2014 the distilled essence, not raw logs
|
|
9534
9257
|
- Over time, review your daily files and update MEMORY.md with what's worth keeping
|
|
@@ -9537,11 +9260,42 @@ Capture what matters. Decisions, context, things to remember. Skip the secrets u
|
|
|
9537
9260
|
|
|
9538
9261
|
- **Memory is limited** \u2014 if you want to remember something, WRITE IT TO A FILE
|
|
9539
9262
|
- "Mental notes" don't survive session restarts. Files do.
|
|
9540
|
-
- When someone says "remember this" \u2192 update
|
|
9541
|
-
- When you learn a lesson \u2192 update AGENTS.md, TOOLS.md, or the relevant skill
|
|
9263
|
+
- When someone says "remember this" \u2192 update \`/daily/YYYY-MM-DD.md\` or relevant file
|
|
9264
|
+
- When you learn a lesson \u2192 update /agent/AGENTS.md, /agent/TOOLS.md, or the relevant skill
|
|
9542
9265
|
- When you make a mistake \u2192 document it so future-you doesn't repeat it
|
|
9543
9266
|
- **Text > Brain** \u{1F4DD}
|
|
9544
9267
|
|
|
9268
|
+
### Project Memory File: \`/PROJECT.md\`
|
|
9269
|
+
\u2192 Describes **how this specific project works** and **how the agent should behave here only.**
|
|
9270
|
+
|
|
9271
|
+
**Store here:**
|
|
9272
|
+
- Project-specific architecture and design patterns
|
|
9273
|
+
- Coding conventions specific to this codebase
|
|
9274
|
+
- Project structure and organization
|
|
9275
|
+
- Testing strategies for this project
|
|
9276
|
+
- Deployment processes and workflows
|
|
9277
|
+
- Team conventions and guidelines
|
|
9278
|
+
|
|
9279
|
+
**Examples:**
|
|
9280
|
+
- "This project uses FastAPI with SQLAlchemy"
|
|
9281
|
+
- "Tests go in tests/ directory mirroring src/ structure"
|
|
9282
|
+
- "All API changes require updating OpenAPI spec"
|
|
9283
|
+
|
|
9284
|
+
### Project Memory Files: \`{project_deepagents_dir}/*.md\`
|
|
9285
|
+
\u2192 Use for **project-specific reference information** and structured notes.
|
|
9286
|
+
|
|
9287
|
+
**Store here:**
|
|
9288
|
+
- API design documentation
|
|
9289
|
+
- Architecture decisions and rationale
|
|
9290
|
+
- Deployment procedures
|
|
9291
|
+
- Common debugging patterns
|
|
9292
|
+
- Onboarding information
|
|
9293
|
+
|
|
9294
|
+
**Examples:**
|
|
9295
|
+
- \`{project_deepagents_dir}/api-design.md\` - REST API patterns used
|
|
9296
|
+
- \`{project_deepagents_dir}/architecture.md\` - System architecture overview
|
|
9297
|
+
- \`{project_deepagents_dir}/deployment.md\` - How to deploy this project
|
|
9298
|
+
|
|
9545
9299
|
## Safety
|
|
9546
9300
|
|
|
9547
9301
|
- Don't exfiltrate private data. Ever.
|
|
@@ -9713,10 +9467,10 @@ Offer suggestions if they're stuck. Have fun with it.
|
|
|
9713
9467
|
|
|
9714
9468
|
Update these files with what you learned:
|
|
9715
9469
|
|
|
9716
|
-
-
|
|
9717
|
-
-
|
|
9470
|
+
- \`/agent/IDENTITY.md\` \u2014 your name, creature, vibe, emoji
|
|
9471
|
+
- \`/agent/USER.md\` \u2014 their name, how to address them, timezone, notes
|
|
9718
9472
|
|
|
9719
|
-
Then open
|
|
9473
|
+
Then open \`/agent/SOUL.md\` together and talk about:
|
|
9720
9474
|
|
|
9721
9475
|
- What matters to them
|
|
9722
9476
|
- How they want you to behave
|
|
@@ -9849,12 +9603,12 @@ async function getBackend2(backend, stateAndStore) {
|
|
|
9849
9603
|
return backend;
|
|
9850
9604
|
}
|
|
9851
9605
|
var BOOTSTRAP_FILE_NAMES = {
|
|
9852
|
-
agents: "AGENTS.md",
|
|
9853
|
-
soul: "SOUL.md",
|
|
9854
|
-
identity: "IDENTITY.md",
|
|
9855
|
-
user: "USER.md",
|
|
9856
|
-
tools: "TOOLS.md",
|
|
9857
|
-
bootstrap: "BOOTSTRAP.md"
|
|
9606
|
+
agents: "/agent/AGENTS.md",
|
|
9607
|
+
soul: "/agent/SOUL.md",
|
|
9608
|
+
identity: "/agent/IDENTITY.md",
|
|
9609
|
+
user: "/agent/USER.md",
|
|
9610
|
+
tools: "/agent/TOOLS.md",
|
|
9611
|
+
bootstrap: "/agent/BOOTSTRAP.md"
|
|
9858
9612
|
};
|
|
9859
9613
|
var BOOTSTRAP_SECTION_HEADERS = {
|
|
9860
9614
|
agents: "## Operating Instructions",
|
|
@@ -9877,14 +9631,14 @@ Document available tools and their usage notes here.`,
|
|
|
9877
9631
|
async function createBootstrapFiles(config, backend, stateAndStore) {
|
|
9878
9632
|
const resolvedBackend = await getBackend2(backend, stateAndStore);
|
|
9879
9633
|
try {
|
|
9880
|
-
const agentsContent = await resolvedBackend.read("/AGENTS.md", 0, 1);
|
|
9634
|
+
const agentsContent = await resolvedBackend.read("/agent/AGENTS.md", 0, 1);
|
|
9881
9635
|
if (!agentsContent.includes("Error:")) {
|
|
9882
9636
|
return;
|
|
9883
9637
|
}
|
|
9884
9638
|
} catch (error) {
|
|
9885
9639
|
}
|
|
9886
9640
|
for (const [key, filename] of Object.entries(BOOTSTRAP_FILE_NAMES)) {
|
|
9887
|
-
const filePath =
|
|
9641
|
+
const filePath = filename;
|
|
9888
9642
|
try {
|
|
9889
9643
|
const content = config[key] || DEFAULT_BOOTSTRAP_CONTENT[key];
|
|
9890
9644
|
await resolvedBackend.write(filePath, content);
|
|
@@ -9898,7 +9652,7 @@ async function buildBootstrapPromptSections(backend, stateAndStore) {
|
|
|
9898
9652
|
const sections = [];
|
|
9899
9653
|
const fileOrder = ["agents", "soul", "identity", "user", "tools", "bootstrap"];
|
|
9900
9654
|
for (const key of fileOrder) {
|
|
9901
|
-
const filePath =
|
|
9655
|
+
const filePath = BOOTSTRAP_FILE_NAMES[key];
|
|
9902
9656
|
try {
|
|
9903
9657
|
const content = await resolvedBackend.read(filePath);
|
|
9904
9658
|
if (content && !content.includes("Error:") && content.trim()) {
|
|
@@ -9934,14 +9688,13 @@ function createClawMiddleware(options = {}) {
|
|
|
9934
9688
|
if (injectBootstrapFiles && backend) {
|
|
9935
9689
|
const stateAndStore = {
|
|
9936
9690
|
state: request.state || {},
|
|
9937
|
-
store: request.store
|
|
9691
|
+
store: request.store,
|
|
9692
|
+
...request.runtime.context.runConfig
|
|
9938
9693
|
};
|
|
9939
9694
|
const bootstrapSections = await buildBootstrapPromptSections(backend, stateAndStore);
|
|
9940
9695
|
if (bootstrapSections.length > 0) {
|
|
9941
9696
|
const bootstrapContext = `
|
|
9942
9697
|
|
|
9943
|
-
|
|
9944
|
-
|
|
9945
9698
|
${bootstrapSections.join("\n\n")}
|
|
9946
9699
|
|
|
9947
9700
|
`;
|
|
@@ -10143,14 +9896,18 @@ ${currentSystemPrompt}` : dateContext;
|
|
|
10143
9896
|
}
|
|
10144
9897
|
|
|
10145
9898
|
// src/agent_lattice/builders/commonMiddleware.ts
|
|
10146
|
-
async function createCommonMiddlewares(middlewareConfigs, filesystemBackend) {
|
|
9899
|
+
async function createCommonMiddlewares(middlewareConfigs, filesystemBackend, fsIsExised) {
|
|
10147
9900
|
const middlewares = [];
|
|
10148
9901
|
middlewares.push(createUnknownToolHandlerMiddleware());
|
|
10149
9902
|
middlewares.push(createModelSelectorMiddleware());
|
|
10150
9903
|
const filesystemConfig = middlewareConfigs.find((m) => m.type === "filesystem");
|
|
10151
|
-
|
|
10152
|
-
|
|
10153
|
-
|
|
9904
|
+
const clawConfig = middlewareConfigs.find((m) => m.type === "claw");
|
|
9905
|
+
const needsFilesystemBackend = filesystemConfig?.enabled || clawConfig?.enabled;
|
|
9906
|
+
if (needsFilesystemBackend && filesystemBackend) {
|
|
9907
|
+
if (!fsIsExised) {
|
|
9908
|
+
const options = { backend: filesystemBackend };
|
|
9909
|
+
middlewares.push(createFilesystemMiddleware(options));
|
|
9910
|
+
}
|
|
10154
9911
|
}
|
|
10155
9912
|
for (const config of middlewareConfigs) {
|
|
10156
9913
|
if (!config.enabled || config.type === "filesystem") continue;
|
|
@@ -10198,12 +9955,14 @@ async function createCommonMiddlewares(middlewareConfigs, filesystemBackend) {
|
|
|
10198
9955
|
break;
|
|
10199
9956
|
case "claw":
|
|
10200
9957
|
if (filesystemBackend) {
|
|
10201
|
-
const
|
|
9958
|
+
const clawMiddlewareConfig = config.config;
|
|
10202
9959
|
middlewares.push(createClawMiddleware({
|
|
10203
9960
|
backend: filesystemBackend,
|
|
10204
|
-
injectBootstrapFiles:
|
|
10205
|
-
bootstrapFiles:
|
|
9961
|
+
injectBootstrapFiles: clawMiddlewareConfig.injectBootstrapFiles ?? true,
|
|
9962
|
+
bootstrapFiles: clawMiddlewareConfig.bootstrapFiles ?? {}
|
|
10206
9963
|
}));
|
|
9964
|
+
} else {
|
|
9965
|
+
console.warn("[claw middleware] Filesystem backend not available. Claw middleware requires filesystem backend to function.");
|
|
10207
9966
|
}
|
|
10208
9967
|
break;
|
|
10209
9968
|
case "date":
|
|
@@ -10211,45 +9970,516 @@ async function createCommonMiddlewares(middlewareConfigs, filesystemBackend) {
|
|
|
10211
9970
|
break;
|
|
10212
9971
|
}
|
|
10213
9972
|
}
|
|
10214
|
-
return middlewares;
|
|
10215
|
-
}
|
|
9973
|
+
return middlewares;
|
|
9974
|
+
}
|
|
9975
|
+
|
|
9976
|
+
// src/deep_agent_new/backends/sandboxFiles.ts
|
|
9977
|
+
var import_sandbox2 = require("@agent-infra/sandbox");
|
|
9978
|
+
var path3 = __toESM(require("path"));
|
|
9979
|
+
var SandboxFilesystem = class {
|
|
9980
|
+
/**
|
|
9981
|
+
* Create a new SandboxFilesystem instance.
|
|
9982
|
+
*
|
|
9983
|
+
* @param options - Configuration options
|
|
9984
|
+
* @param options.baseURL - Base URL of the sandbox service (default: 'http://localhost:8080')
|
|
9985
|
+
* @param options.maxFileSizeMb - Maximum file size in MB (default: 10)
|
|
9986
|
+
* @param options.sandboxInstance - Optional Sandbox instance (if provided, baseURL is ignored)
|
|
9987
|
+
*/
|
|
9988
|
+
constructor(options = {}) {
|
|
9989
|
+
const {
|
|
9990
|
+
baseURL = "http://localhost:8080",
|
|
9991
|
+
workingDirectory = "/",
|
|
9992
|
+
maxFileSizeMb = 10,
|
|
9993
|
+
sandboxInstance
|
|
9994
|
+
} = options;
|
|
9995
|
+
this.sandbox = sandboxInstance || new import_sandbox2.SandboxClient({ baseUrl: baseURL, environment: "" });
|
|
9996
|
+
this.sandbox.mcp.listMcpServers().then((servers) => {
|
|
9997
|
+
});
|
|
9998
|
+
this.sandbox.mcp.listMcpTools("browser").then((tools) => {
|
|
9999
|
+
});
|
|
10000
|
+
this.baseURL = baseURL;
|
|
10001
|
+
this.maxFileSizeBytes = maxFileSizeMb * 1024 * 1024;
|
|
10002
|
+
this.workingDirectory = workingDirectory;
|
|
10003
|
+
this.homeDir = "/home/gem";
|
|
10004
|
+
}
|
|
10005
|
+
resolvePath(virtualPath) {
|
|
10006
|
+
return path3.join(this.homeDir, this.workingDirectory, virtualPath);
|
|
10007
|
+
}
|
|
10008
|
+
/**
|
|
10009
|
+
* Convert a real filesystem path to a virtual path.
|
|
10010
|
+
*
|
|
10011
|
+
* @param realPath - Real filesystem path
|
|
10012
|
+
* @returns Virtual path starting with /
|
|
10013
|
+
*/
|
|
10014
|
+
toVirtualPath(realPath) {
|
|
10015
|
+
const rootPath = path3.join(this.homeDir, this.workingDirectory);
|
|
10016
|
+
const relative4 = path3.relative(rootPath, realPath);
|
|
10017
|
+
const normalized = relative4.split(path3.sep).join("/");
|
|
10018
|
+
return "/" + normalized;
|
|
10019
|
+
}
|
|
10020
|
+
/**
|
|
10021
|
+
* List files and directories in the specified directory (non-recursive).
|
|
10022
|
+
*
|
|
10023
|
+
* @param dirPath - Virtual directory path (must start with /)
|
|
10024
|
+
* @returns List of FileInfo objects for files and directories directly in the directory.
|
|
10025
|
+
* Directories have a trailing / in their path and is_dir=true.
|
|
10026
|
+
*/
|
|
10027
|
+
async lsInfo(dirPath) {
|
|
10028
|
+
try {
|
|
10029
|
+
const resolvedPath = this.resolvePath(dirPath);
|
|
10030
|
+
const result = await this.sandbox.file.listPath({
|
|
10031
|
+
path: resolvedPath,
|
|
10032
|
+
recursive: false,
|
|
10033
|
+
show_hidden: false,
|
|
10034
|
+
max_depth: 0,
|
|
10035
|
+
include_size: false,
|
|
10036
|
+
include_permissions: false,
|
|
10037
|
+
sort_by: "name",
|
|
10038
|
+
sort_desc: false
|
|
10039
|
+
});
|
|
10040
|
+
if (!result.ok) {
|
|
10041
|
+
throw result.error;
|
|
10042
|
+
}
|
|
10043
|
+
const files = result.body?.data?.files?.map((file) => ({
|
|
10044
|
+
path: this.toVirtualPath(file.path),
|
|
10045
|
+
is_dir: file.is_directory,
|
|
10046
|
+
size: file.size,
|
|
10047
|
+
modified_at: file.modified_time
|
|
10048
|
+
})) || [];
|
|
10049
|
+
return files;
|
|
10050
|
+
} catch (e) {
|
|
10051
|
+
console.error(`Error listing files in ${dirPath}:`, e);
|
|
10052
|
+
return [];
|
|
10053
|
+
}
|
|
10054
|
+
}
|
|
10055
|
+
/**
|
|
10056
|
+
* Read file content with line numbers.
|
|
10057
|
+
*
|
|
10058
|
+
* @param filePath - Virtual file path (must start with /)
|
|
10059
|
+
* @param offset - Line offset to start reading from (0-indexed)
|
|
10060
|
+
* @param limit - Maximum number of lines to read
|
|
10061
|
+
* @returns Formatted file content with line numbers, or error message
|
|
10062
|
+
*/
|
|
10063
|
+
async read(filePath, offset = 0, limit = 1e4) {
|
|
10064
|
+
try {
|
|
10065
|
+
const resolvedPath = this.resolvePath(filePath);
|
|
10066
|
+
let content;
|
|
10067
|
+
const result = await this.sandbox.file.readFile({
|
|
10068
|
+
file: resolvedPath,
|
|
10069
|
+
start_line: offset,
|
|
10070
|
+
end_line: limit
|
|
10071
|
+
});
|
|
10072
|
+
if (!result.ok) {
|
|
10073
|
+
throw result.error;
|
|
10074
|
+
}
|
|
10075
|
+
content = result.body?.data?.content || "";
|
|
10076
|
+
return content;
|
|
10077
|
+
} catch (e) {
|
|
10078
|
+
return `Error: File '${filePath}' not found`;
|
|
10079
|
+
}
|
|
10080
|
+
}
|
|
10081
|
+
/**
|
|
10082
|
+
* Read file content as raw FileData.
|
|
10083
|
+
*
|
|
10084
|
+
* @param filePath - Virtual file path (must start with /)
|
|
10085
|
+
* @returns Raw file content as FileData
|
|
10086
|
+
*/
|
|
10087
|
+
async readRaw(filePath) {
|
|
10088
|
+
try {
|
|
10089
|
+
const content = await this.read(filePath);
|
|
10090
|
+
return {
|
|
10091
|
+
content: content.split("\n"),
|
|
10092
|
+
created_at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
10093
|
+
modified_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
10094
|
+
};
|
|
10095
|
+
} catch (e) {
|
|
10096
|
+
throw new Error(`Error reading file '${filePath}': ${e.message}`);
|
|
10097
|
+
}
|
|
10098
|
+
}
|
|
10099
|
+
/**
|
|
10100
|
+
* Create a new file with content.
|
|
10101
|
+
* Returns WriteResult. External storage sets filesUpdate=null.
|
|
10102
|
+
*
|
|
10103
|
+
* @param filePath - Virtual file path (must start with /)
|
|
10104
|
+
* @param content - File content as string
|
|
10105
|
+
* @returns WriteResult with error populated on failure
|
|
10106
|
+
*/
|
|
10107
|
+
async write(filePath, content) {
|
|
10108
|
+
try {
|
|
10109
|
+
const resolvedPath = this.resolvePath(filePath);
|
|
10110
|
+
const result = await this.sandbox.file.writeFile({
|
|
10111
|
+
file: resolvedPath,
|
|
10112
|
+
content,
|
|
10113
|
+
"encoding": "utf-8",
|
|
10114
|
+
"append": false
|
|
10115
|
+
// sudo: true
|
|
10116
|
+
});
|
|
10117
|
+
if (!result.ok) {
|
|
10118
|
+
console.error(result.error);
|
|
10119
|
+
throw result.error;
|
|
10120
|
+
}
|
|
10121
|
+
return {
|
|
10122
|
+
path: filePath,
|
|
10123
|
+
filesUpdate: {
|
|
10124
|
+
[filePath]: {
|
|
10125
|
+
content: content.split("\n"),
|
|
10126
|
+
created_at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
10127
|
+
modified_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
10128
|
+
}
|
|
10129
|
+
}
|
|
10130
|
+
};
|
|
10131
|
+
} catch (e) {
|
|
10132
|
+
throw new Error(`Error writing file '${filePath}': ${e.message}`);
|
|
10133
|
+
}
|
|
10134
|
+
}
|
|
10135
|
+
/**
|
|
10136
|
+
* Edit a file by replacing string occurrences.
|
|
10137
|
+
* Returns EditResult. External storage sets filesUpdate=null.
|
|
10138
|
+
*
|
|
10139
|
+
* @param filePath - Virtual file path (must start with /)
|
|
10140
|
+
* @param oldString - String to find and replace
|
|
10141
|
+
* @param newString - Replacement string
|
|
10142
|
+
* @param replaceAll - If true, replace all occurrences (default: false)
|
|
10143
|
+
* @returns EditResult with error, path, filesUpdate, and occurrences
|
|
10144
|
+
*/
|
|
10145
|
+
async edit(filePath, oldString, newString, replaceAll = false) {
|
|
10146
|
+
try {
|
|
10147
|
+
const resolvedPath = this.resolvePath(filePath);
|
|
10148
|
+
const result = await this.sandbox.file.strReplaceEditor({
|
|
10149
|
+
command: "str_replace",
|
|
10150
|
+
path: resolvedPath,
|
|
10151
|
+
old_str: oldString,
|
|
10152
|
+
new_str: newString,
|
|
10153
|
+
replace_mode: replaceAll ? "ALL" : "FIRST"
|
|
10154
|
+
});
|
|
10155
|
+
if (!result.ok) {
|
|
10156
|
+
throw result.error;
|
|
10157
|
+
}
|
|
10158
|
+
return {
|
|
10159
|
+
path: filePath,
|
|
10160
|
+
filesUpdate: null
|
|
10161
|
+
};
|
|
10162
|
+
} catch (e) {
|
|
10163
|
+
throw new Error(`Error editing file '${filePath}': ${e.message}`);
|
|
10164
|
+
}
|
|
10165
|
+
}
|
|
10166
|
+
/**
|
|
10167
|
+
* Structured search results or error string for invalid input.
|
|
10168
|
+
*
|
|
10169
|
+
* Searches file contents for a regex pattern within the sandbox.
|
|
10170
|
+
*
|
|
10171
|
+
* @param pattern - Regex pattern to search for
|
|
10172
|
+
* @param searchPath - Base path to search from (default: "/")
|
|
10173
|
+
* @param glob - Optional glob pattern to filter files (e.g., "*.py")
|
|
10174
|
+
* @returns List of GrepMatch objects or error string for invalid regex
|
|
10175
|
+
*/
|
|
10176
|
+
async grepRaw(pattern, searchPath = "/", glob = null) {
|
|
10177
|
+
let baseFull;
|
|
10178
|
+
baseFull = this.resolvePath(searchPath || "/");
|
|
10179
|
+
const result = await this.sandbox.file.findFiles({
|
|
10180
|
+
path: baseFull,
|
|
10181
|
+
glob: glob || "**/*"
|
|
10182
|
+
});
|
|
10183
|
+
if (!result.ok) {
|
|
10184
|
+
throw result.error;
|
|
10185
|
+
}
|
|
10186
|
+
const filePaths = result.body?.data?.files || [];
|
|
10187
|
+
const matches = [];
|
|
10188
|
+
for (const absolutePath of filePaths) {
|
|
10189
|
+
const fileData = await this.sandbox.file.searchInFile({
|
|
10190
|
+
file: absolutePath,
|
|
10191
|
+
regex: pattern
|
|
10192
|
+
});
|
|
10193
|
+
if (!fileData.ok) {
|
|
10194
|
+
continue;
|
|
10195
|
+
}
|
|
10196
|
+
const matchesData = fileData.body?.data?.matches || [];
|
|
10197
|
+
const matchLines = fileData.body?.data?.line_numbers || [];
|
|
10198
|
+
matchesData.forEach((match, index) => {
|
|
10199
|
+
matches.push({
|
|
10200
|
+
path: this.toVirtualPath(absolutePath),
|
|
10201
|
+
line: matchLines[index],
|
|
10202
|
+
text: match
|
|
10203
|
+
});
|
|
10204
|
+
});
|
|
10205
|
+
}
|
|
10206
|
+
return matches;
|
|
10207
|
+
}
|
|
10208
|
+
/**
|
|
10209
|
+
* Structured glob matching returning FileInfo objects.
|
|
10210
|
+
*
|
|
10211
|
+
* @param pattern - Glob pattern (e.g., `*.py`, `**\/*.ts`)
|
|
10212
|
+
* @param searchPath - Base path to search from (default: "/")
|
|
10213
|
+
* @returns List of FileInfo objects matching the pattern
|
|
10214
|
+
*/
|
|
10215
|
+
async globInfo(pattern, searchPath = "/") {
|
|
10216
|
+
if (pattern.startsWith("/")) {
|
|
10217
|
+
pattern = pattern.substring(1);
|
|
10218
|
+
}
|
|
10219
|
+
const resolvedSearchPath = this.resolvePath(searchPath);
|
|
10220
|
+
const result = await this.sandbox.file.findFiles({
|
|
10221
|
+
path: resolvedSearchPath,
|
|
10222
|
+
glob: pattern || "**/*"
|
|
10223
|
+
});
|
|
10224
|
+
if (!result.ok) {
|
|
10225
|
+
throw result.error;
|
|
10226
|
+
}
|
|
10227
|
+
const results = [];
|
|
10228
|
+
for (const filePath of result.body?.data?.files || []) {
|
|
10229
|
+
const fileInfo = await this.sandbox.file.listPath({
|
|
10230
|
+
path: filePath,
|
|
10231
|
+
recursive: false,
|
|
10232
|
+
show_hidden: false,
|
|
10233
|
+
max_depth: 1,
|
|
10234
|
+
include_size: false,
|
|
10235
|
+
include_permissions: false
|
|
10236
|
+
});
|
|
10237
|
+
if (!fileInfo.ok) {
|
|
10238
|
+
continue;
|
|
10239
|
+
}
|
|
10240
|
+
results.push({
|
|
10241
|
+
path: this.toVirtualPath(filePath),
|
|
10242
|
+
is_dir: false,
|
|
10243
|
+
size: fileInfo.body?.data?.files?.[0]?.size,
|
|
10244
|
+
modified_at: fileInfo.body?.data?.files?.[0]?.modified_time
|
|
10245
|
+
});
|
|
10246
|
+
}
|
|
10247
|
+
return results;
|
|
10248
|
+
}
|
|
10249
|
+
};
|
|
10250
|
+
|
|
10251
|
+
// src/deep_agent_new/backends/composite.ts
|
|
10252
|
+
var CompositeBackend = class {
|
|
10253
|
+
constructor(defaultBackend, routes) {
|
|
10254
|
+
this.default = defaultBackend;
|
|
10255
|
+
this.routes = routes;
|
|
10256
|
+
this.sortedRoutes = Object.entries(routes).sort(
|
|
10257
|
+
(a, b) => b[0].length - a[0].length
|
|
10258
|
+
);
|
|
10259
|
+
}
|
|
10260
|
+
/**
|
|
10261
|
+
* Determine which backend handles this key and strip prefix.
|
|
10262
|
+
*
|
|
10263
|
+
* @param key - Original file path
|
|
10264
|
+
* @returns Tuple of [backend, stripped_key] where stripped_key has the route
|
|
10265
|
+
* prefix removed (but keeps leading slash).
|
|
10266
|
+
*/
|
|
10267
|
+
getBackendAndKey(key) {
|
|
10268
|
+
for (const [prefix, backend] of this.sortedRoutes) {
|
|
10269
|
+
if (key.startsWith(prefix)) {
|
|
10270
|
+
const suffix = key.substring(prefix.length);
|
|
10271
|
+
const strippedKey = suffix ? "/" + suffix : "/";
|
|
10272
|
+
return [backend, strippedKey];
|
|
10273
|
+
}
|
|
10274
|
+
}
|
|
10275
|
+
return [this.default, key];
|
|
10276
|
+
}
|
|
10277
|
+
/**
|
|
10278
|
+
* List files and directories in the specified directory (non-recursive).
|
|
10279
|
+
*
|
|
10280
|
+
* @param path - Absolute path to directory
|
|
10281
|
+
* @returns List of FileInfo objects with route prefixes added, for files and directories
|
|
10282
|
+
* directly in the directory. Directories have a trailing / in their path and is_dir=true.
|
|
10283
|
+
*/
|
|
10284
|
+
async lsInfo(path5) {
|
|
10285
|
+
for (const [routePrefix, backend] of this.sortedRoutes) {
|
|
10286
|
+
if (path5.startsWith(routePrefix.replace(/\/$/, ""))) {
|
|
10287
|
+
const suffix = path5.substring(routePrefix.length);
|
|
10288
|
+
const searchPath = suffix ? "/" + suffix : "/";
|
|
10289
|
+
const infos = await backend.lsInfo(searchPath);
|
|
10290
|
+
const prefixed = [];
|
|
10291
|
+
for (const fi of infos) {
|
|
10292
|
+
prefixed.push({
|
|
10293
|
+
...fi,
|
|
10294
|
+
path: routePrefix.slice(0, -1) + fi.path
|
|
10295
|
+
});
|
|
10296
|
+
}
|
|
10297
|
+
return prefixed;
|
|
10298
|
+
}
|
|
10299
|
+
}
|
|
10300
|
+
if (path5 === "/") {
|
|
10301
|
+
const results = [];
|
|
10302
|
+
const defaultInfos = await this.default.lsInfo(path5);
|
|
10303
|
+
results.push(...defaultInfos);
|
|
10304
|
+
for (const [routePrefix] of this.sortedRoutes) {
|
|
10305
|
+
results.push({
|
|
10306
|
+
path: routePrefix,
|
|
10307
|
+
is_dir: true,
|
|
10308
|
+
size: 0,
|
|
10309
|
+
modified_at: ""
|
|
10310
|
+
});
|
|
10311
|
+
}
|
|
10312
|
+
results.sort((a, b) => a.path.localeCompare(b.path));
|
|
10313
|
+
return results;
|
|
10314
|
+
}
|
|
10315
|
+
return await this.default.lsInfo(path5);
|
|
10316
|
+
}
|
|
10317
|
+
/**
|
|
10318
|
+
* Read file content, routing to appropriate backend.
|
|
10319
|
+
*
|
|
10320
|
+
* @param filePath - Absolute file path
|
|
10321
|
+
* @param offset - Line offset to start reading from (0-indexed)
|
|
10322
|
+
* @param limit - Maximum number of lines to read
|
|
10323
|
+
* @returns Formatted file content with line numbers, or error message
|
|
10324
|
+
*/
|
|
10325
|
+
async read(filePath, offset = 0, limit = 2e3) {
|
|
10326
|
+
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
10327
|
+
return await backend.read(strippedKey, offset, limit);
|
|
10328
|
+
}
|
|
10329
|
+
/**
|
|
10330
|
+
* Read file content as raw FileData.
|
|
10331
|
+
*
|
|
10332
|
+
* @param filePath - Absolute file path
|
|
10333
|
+
* @returns Raw file content as FileData
|
|
10334
|
+
*/
|
|
10335
|
+
async readRaw(filePath) {
|
|
10336
|
+
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
10337
|
+
return await backend.readRaw(strippedKey);
|
|
10338
|
+
}
|
|
10339
|
+
/**
|
|
10340
|
+
* Structured search results or error string for invalid input.
|
|
10341
|
+
*/
|
|
10342
|
+
async grepRaw(pattern, path5 = "/", glob = null) {
|
|
10343
|
+
for (const [routePrefix, backend] of this.sortedRoutes) {
|
|
10344
|
+
if (path5.startsWith(routePrefix.replace(/\/$/, ""))) {
|
|
10345
|
+
const searchPath = path5.substring(routePrefix.length - 1);
|
|
10346
|
+
const raw = await backend.grepRaw(pattern, searchPath || "/", glob);
|
|
10347
|
+
if (typeof raw === "string") {
|
|
10348
|
+
return raw;
|
|
10349
|
+
}
|
|
10350
|
+
return raw.map((m) => ({
|
|
10351
|
+
...m,
|
|
10352
|
+
path: routePrefix.slice(0, -1) + m.path
|
|
10353
|
+
}));
|
|
10354
|
+
}
|
|
10355
|
+
}
|
|
10356
|
+
const allMatches = [];
|
|
10357
|
+
const rawDefault = await this.default.grepRaw(pattern, path5, glob);
|
|
10358
|
+
if (typeof rawDefault === "string") {
|
|
10359
|
+
return rawDefault;
|
|
10360
|
+
}
|
|
10361
|
+
allMatches.push(...rawDefault);
|
|
10362
|
+
for (const [routePrefix, backend] of Object.entries(this.routes)) {
|
|
10363
|
+
const raw = await backend.grepRaw(pattern, "/", glob);
|
|
10364
|
+
if (typeof raw === "string") {
|
|
10365
|
+
return raw;
|
|
10366
|
+
}
|
|
10367
|
+
allMatches.push(
|
|
10368
|
+
...raw.map((m) => ({
|
|
10369
|
+
...m,
|
|
10370
|
+
path: routePrefix.slice(0, -1) + m.path
|
|
10371
|
+
}))
|
|
10372
|
+
);
|
|
10373
|
+
}
|
|
10374
|
+
return allMatches;
|
|
10375
|
+
}
|
|
10376
|
+
/**
|
|
10377
|
+
* Structured glob matching returning FileInfo objects.
|
|
10378
|
+
*/
|
|
10379
|
+
async globInfo(pattern, path5 = "/") {
|
|
10380
|
+
const results = [];
|
|
10381
|
+
for (const [routePrefix, backend] of this.sortedRoutes) {
|
|
10382
|
+
if (path5.startsWith(routePrefix.replace(/\/$/, ""))) {
|
|
10383
|
+
const searchPath = path5.substring(routePrefix.length - 1);
|
|
10384
|
+
const infos = await backend.globInfo(pattern, searchPath || "/");
|
|
10385
|
+
return infos.map((fi) => ({
|
|
10386
|
+
...fi,
|
|
10387
|
+
path: routePrefix.slice(0, -1) + fi.path
|
|
10388
|
+
}));
|
|
10389
|
+
}
|
|
10390
|
+
}
|
|
10391
|
+
const defaultInfos = await this.default.globInfo(pattern, path5);
|
|
10392
|
+
results.push(...defaultInfos);
|
|
10393
|
+
for (const [routePrefix, backend] of Object.entries(this.routes)) {
|
|
10394
|
+
const infos = await backend.globInfo(pattern, "/");
|
|
10395
|
+
results.push(
|
|
10396
|
+
...infos.map((fi) => ({
|
|
10397
|
+
...fi,
|
|
10398
|
+
path: routePrefix.slice(0, -1) + fi.path
|
|
10399
|
+
}))
|
|
10400
|
+
);
|
|
10401
|
+
}
|
|
10402
|
+
results.sort((a, b) => a.path.localeCompare(b.path));
|
|
10403
|
+
return results;
|
|
10404
|
+
}
|
|
10405
|
+
/**
|
|
10406
|
+
* Create a new file, routing to appropriate backend.
|
|
10407
|
+
*
|
|
10408
|
+
* @param filePath - Absolute file path
|
|
10409
|
+
* @param content - File content as string
|
|
10410
|
+
* @returns WriteResult with path or error
|
|
10411
|
+
*/
|
|
10412
|
+
async write(filePath, content) {
|
|
10413
|
+
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
10414
|
+
return await backend.write(strippedKey, content);
|
|
10415
|
+
}
|
|
10416
|
+
/**
|
|
10417
|
+
* Edit a file, routing to appropriate backend.
|
|
10418
|
+
*
|
|
10419
|
+
* @param filePath - Absolute file path
|
|
10420
|
+
* @param oldString - String to find and replace
|
|
10421
|
+
* @param newString - Replacement string
|
|
10422
|
+
* @param replaceAll - If true, replace all occurrences
|
|
10423
|
+
* @returns EditResult with path, occurrences, or error
|
|
10424
|
+
*/
|
|
10425
|
+
async edit(filePath, oldString, newString, replaceAll = false) {
|
|
10426
|
+
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
10427
|
+
return await backend.edit(strippedKey, oldString, newString, replaceAll);
|
|
10428
|
+
}
|
|
10429
|
+
};
|
|
10216
10430
|
|
|
10217
|
-
// src/agent_lattice/builders/
|
|
10218
|
-
|
|
10219
|
-
|
|
10220
|
-
|
|
10221
|
-
|
|
10222
|
-
|
|
10431
|
+
// src/agent_lattice/builders/filesystemBackend.ts
|
|
10432
|
+
function createFilesystemBackendFactory(middlewareConfigs, defualtRootLevel = "project", routesLevelConfig = {
|
|
10433
|
+
"/agent/": "agent"
|
|
10434
|
+
//默认配置 agent目录就是agent级别的
|
|
10435
|
+
}) {
|
|
10436
|
+
const filesystemConfig = middlewareConfigs.find((m) => m.type === "filesystem");
|
|
10437
|
+
if (!filesystemConfig || !filesystemConfig.enabled) {
|
|
10438
|
+
return void 0;
|
|
10439
|
+
}
|
|
10440
|
+
const isolatedLevel = filesystemConfig.config?.isolatedLevel || "global";
|
|
10441
|
+
return async (stateAndStore) => {
|
|
10442
|
+
const { tenantId, workspaceId, projectId, assistant_id } = stateAndStore;
|
|
10443
|
+
let sandboxName = "global";
|
|
10444
|
+
if (isolatedLevel === "agent") {
|
|
10445
|
+
sandboxName = "agent";
|
|
10446
|
+
} else if (isolatedLevel === "thread") {
|
|
10447
|
+
sandboxName = "thread";
|
|
10223
10448
|
}
|
|
10224
|
-
const
|
|
10225
|
-
|
|
10226
|
-
|
|
10227
|
-
|
|
10228
|
-
|
|
10229
|
-
let
|
|
10230
|
-
if (
|
|
10231
|
-
|
|
10232
|
-
} else if (
|
|
10233
|
-
|
|
10234
|
-
}
|
|
10235
|
-
const sandboxManager = sandboxLatticeManager.getSandboxLattice("default");
|
|
10236
|
-
if (!sandboxManager) {
|
|
10237
|
-
throw new Error("Sandbox manager not found");
|
|
10238
|
-
}
|
|
10239
|
-
let workingDirectory = "/";
|
|
10240
|
-
if (workspaceId && projectId) {
|
|
10241
|
-
if (tenantId) {
|
|
10242
|
-
workingDirectory = `/tenants/${tenantId}/workspaces/${workspaceId}/${projectId}`;
|
|
10243
|
-
} else {
|
|
10244
|
-
workingDirectory = `/${workspaceId}/${projectId}`;
|
|
10245
|
-
}
|
|
10449
|
+
const sandboxManager = sandboxLatticeManager.getSandboxLattice("default");
|
|
10450
|
+
if (!sandboxManager) {
|
|
10451
|
+
throw new Error("Sandbox manager not found");
|
|
10452
|
+
}
|
|
10453
|
+
const getWS = (rootLevel) => {
|
|
10454
|
+
let workingDirectory = `/tenants/${tenantId}`;
|
|
10455
|
+
if (assistant_id && rootLevel === "agent") {
|
|
10456
|
+
workingDirectory = `/tenants/${tenantId}/agents/${assistant_id}`;
|
|
10457
|
+
} else if (workspaceId && projectId && rootLevel === "project") {
|
|
10458
|
+
workingDirectory = `/tenants/${tenantId}/workspaces/${workspaceId}/${projectId}`;
|
|
10246
10459
|
}
|
|
10247
|
-
return
|
|
10248
|
-
sandboxInstance: await sandboxManager.createSandbox(sandboxName),
|
|
10249
|
-
workingDirectory
|
|
10250
|
-
});
|
|
10460
|
+
return workingDirectory;
|
|
10251
10461
|
};
|
|
10252
|
-
|
|
10462
|
+
const sandboxInstance = await sandboxManager.createSandbox(sandboxName);
|
|
10463
|
+
const sandboxfs = new SandboxFilesystem({
|
|
10464
|
+
sandboxInstance,
|
|
10465
|
+
workingDirectory: getWS(defualtRootLevel)
|
|
10466
|
+
});
|
|
10467
|
+
const routers = Object.keys(routesLevelConfig).reduce((pre, curr) => ({
|
|
10468
|
+
...pre,
|
|
10469
|
+
[curr]: new SandboxFilesystem({
|
|
10470
|
+
sandboxInstance,
|
|
10471
|
+
workingDirectory: getWS(routesLevelConfig[curr])
|
|
10472
|
+
})
|
|
10473
|
+
}), {});
|
|
10474
|
+
const compositeBackend = new CompositeBackend(sandboxfs, {
|
|
10475
|
+
...routers
|
|
10476
|
+
});
|
|
10477
|
+
return compositeBackend;
|
|
10478
|
+
};
|
|
10479
|
+
}
|
|
10480
|
+
|
|
10481
|
+
// src/agent_lattice/builders/ReActAgentGraphBuilder.ts
|
|
10482
|
+
var ReActAgentGraphBuilder = class {
|
|
10253
10483
|
async createMiddlewares(middlewareConfigs) {
|
|
10254
10484
|
return await createCommonMiddlewares(middlewareConfigs);
|
|
10255
10485
|
}
|
|
@@ -10267,7 +10497,7 @@ var ReActAgentGraphBuilder = class {
|
|
|
10267
10497
|
}).filter((tool51) => tool51 !== void 0);
|
|
10268
10498
|
const stateSchema2 = createReactAgentSchema(params.stateSchema);
|
|
10269
10499
|
const middlewareConfigs = params.middleware || [];
|
|
10270
|
-
const filesystemBackend =
|
|
10500
|
+
const filesystemBackend = createFilesystemBackendFactory(middlewareConfigs);
|
|
10271
10501
|
const middlewares = await createCommonMiddlewares(middlewareConfigs, filesystemBackend);
|
|
10272
10502
|
return (0, import_langchain55.createAgent)({
|
|
10273
10503
|
model: params.model,
|
|
@@ -11893,186 +12123,6 @@ var FilesystemBackend = class {
|
|
|
11893
12123
|
}
|
|
11894
12124
|
};
|
|
11895
12125
|
|
|
11896
|
-
// src/deep_agent_new/backends/composite.ts
|
|
11897
|
-
var CompositeBackend = class {
|
|
11898
|
-
constructor(defaultBackend, routes) {
|
|
11899
|
-
this.default = defaultBackend;
|
|
11900
|
-
this.routes = routes;
|
|
11901
|
-
this.sortedRoutes = Object.entries(routes).sort(
|
|
11902
|
-
(a, b) => b[0].length - a[0].length
|
|
11903
|
-
);
|
|
11904
|
-
}
|
|
11905
|
-
/**
|
|
11906
|
-
* Determine which backend handles this key and strip prefix.
|
|
11907
|
-
*
|
|
11908
|
-
* @param key - Original file path
|
|
11909
|
-
* @returns Tuple of [backend, stripped_key] where stripped_key has the route
|
|
11910
|
-
* prefix removed (but keeps leading slash).
|
|
11911
|
-
*/
|
|
11912
|
-
getBackendAndKey(key) {
|
|
11913
|
-
for (const [prefix, backend] of this.sortedRoutes) {
|
|
11914
|
-
if (key.startsWith(prefix)) {
|
|
11915
|
-
const suffix = key.substring(prefix.length);
|
|
11916
|
-
const strippedKey = suffix ? "/" + suffix : "/";
|
|
11917
|
-
return [backend, strippedKey];
|
|
11918
|
-
}
|
|
11919
|
-
}
|
|
11920
|
-
return [this.default, key];
|
|
11921
|
-
}
|
|
11922
|
-
/**
|
|
11923
|
-
* List files and directories in the specified directory (non-recursive).
|
|
11924
|
-
*
|
|
11925
|
-
* @param path - Absolute path to directory
|
|
11926
|
-
* @returns List of FileInfo objects with route prefixes added, for files and directories
|
|
11927
|
-
* directly in the directory. Directories have a trailing / in their path and is_dir=true.
|
|
11928
|
-
*/
|
|
11929
|
-
async lsInfo(path5) {
|
|
11930
|
-
for (const [routePrefix, backend] of this.sortedRoutes) {
|
|
11931
|
-
if (path5.startsWith(routePrefix.replace(/\/$/, ""))) {
|
|
11932
|
-
const suffix = path5.substring(routePrefix.length);
|
|
11933
|
-
const searchPath = suffix ? "/" + suffix : "/";
|
|
11934
|
-
const infos = await backend.lsInfo(searchPath);
|
|
11935
|
-
const prefixed = [];
|
|
11936
|
-
for (const fi of infos) {
|
|
11937
|
-
prefixed.push({
|
|
11938
|
-
...fi,
|
|
11939
|
-
path: routePrefix.slice(0, -1) + fi.path
|
|
11940
|
-
});
|
|
11941
|
-
}
|
|
11942
|
-
return prefixed;
|
|
11943
|
-
}
|
|
11944
|
-
}
|
|
11945
|
-
if (path5 === "/") {
|
|
11946
|
-
const results = [];
|
|
11947
|
-
const defaultInfos = await this.default.lsInfo(path5);
|
|
11948
|
-
results.push(...defaultInfos);
|
|
11949
|
-
for (const [routePrefix] of this.sortedRoutes) {
|
|
11950
|
-
results.push({
|
|
11951
|
-
path: routePrefix,
|
|
11952
|
-
is_dir: true,
|
|
11953
|
-
size: 0,
|
|
11954
|
-
modified_at: ""
|
|
11955
|
-
});
|
|
11956
|
-
}
|
|
11957
|
-
results.sort((a, b) => a.path.localeCompare(b.path));
|
|
11958
|
-
return results;
|
|
11959
|
-
}
|
|
11960
|
-
return await this.default.lsInfo(path5);
|
|
11961
|
-
}
|
|
11962
|
-
/**
|
|
11963
|
-
* Read file content, routing to appropriate backend.
|
|
11964
|
-
*
|
|
11965
|
-
* @param filePath - Absolute file path
|
|
11966
|
-
* @param offset - Line offset to start reading from (0-indexed)
|
|
11967
|
-
* @param limit - Maximum number of lines to read
|
|
11968
|
-
* @returns Formatted file content with line numbers, or error message
|
|
11969
|
-
*/
|
|
11970
|
-
async read(filePath, offset = 0, limit = 2e3) {
|
|
11971
|
-
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
11972
|
-
return await backend.read(strippedKey, offset, limit);
|
|
11973
|
-
}
|
|
11974
|
-
/**
|
|
11975
|
-
* Read file content as raw FileData.
|
|
11976
|
-
*
|
|
11977
|
-
* @param filePath - Absolute file path
|
|
11978
|
-
* @returns Raw file content as FileData
|
|
11979
|
-
*/
|
|
11980
|
-
async readRaw(filePath) {
|
|
11981
|
-
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
11982
|
-
return await backend.readRaw(strippedKey);
|
|
11983
|
-
}
|
|
11984
|
-
/**
|
|
11985
|
-
* Structured search results or error string for invalid input.
|
|
11986
|
-
*/
|
|
11987
|
-
async grepRaw(pattern, path5 = "/", glob = null) {
|
|
11988
|
-
for (const [routePrefix, backend] of this.sortedRoutes) {
|
|
11989
|
-
if (path5.startsWith(routePrefix.replace(/\/$/, ""))) {
|
|
11990
|
-
const searchPath = path5.substring(routePrefix.length - 1);
|
|
11991
|
-
const raw = await backend.grepRaw(pattern, searchPath || "/", glob);
|
|
11992
|
-
if (typeof raw === "string") {
|
|
11993
|
-
return raw;
|
|
11994
|
-
}
|
|
11995
|
-
return raw.map((m) => ({
|
|
11996
|
-
...m,
|
|
11997
|
-
path: routePrefix.slice(0, -1) + m.path
|
|
11998
|
-
}));
|
|
11999
|
-
}
|
|
12000
|
-
}
|
|
12001
|
-
const allMatches = [];
|
|
12002
|
-
const rawDefault = await this.default.grepRaw(pattern, path5, glob);
|
|
12003
|
-
if (typeof rawDefault === "string") {
|
|
12004
|
-
return rawDefault;
|
|
12005
|
-
}
|
|
12006
|
-
allMatches.push(...rawDefault);
|
|
12007
|
-
for (const [routePrefix, backend] of Object.entries(this.routes)) {
|
|
12008
|
-
const raw = await backend.grepRaw(pattern, "/", glob);
|
|
12009
|
-
if (typeof raw === "string") {
|
|
12010
|
-
return raw;
|
|
12011
|
-
}
|
|
12012
|
-
allMatches.push(
|
|
12013
|
-
...raw.map((m) => ({
|
|
12014
|
-
...m,
|
|
12015
|
-
path: routePrefix.slice(0, -1) + m.path
|
|
12016
|
-
}))
|
|
12017
|
-
);
|
|
12018
|
-
}
|
|
12019
|
-
return allMatches;
|
|
12020
|
-
}
|
|
12021
|
-
/**
|
|
12022
|
-
* Structured glob matching returning FileInfo objects.
|
|
12023
|
-
*/
|
|
12024
|
-
async globInfo(pattern, path5 = "/") {
|
|
12025
|
-
const results = [];
|
|
12026
|
-
for (const [routePrefix, backend] of this.sortedRoutes) {
|
|
12027
|
-
if (path5.startsWith(routePrefix.replace(/\/$/, ""))) {
|
|
12028
|
-
const searchPath = path5.substring(routePrefix.length - 1);
|
|
12029
|
-
const infos = await backend.globInfo(pattern, searchPath || "/");
|
|
12030
|
-
return infos.map((fi) => ({
|
|
12031
|
-
...fi,
|
|
12032
|
-
path: routePrefix.slice(0, -1) + fi.path
|
|
12033
|
-
}));
|
|
12034
|
-
}
|
|
12035
|
-
}
|
|
12036
|
-
const defaultInfos = await this.default.globInfo(pattern, path5);
|
|
12037
|
-
results.push(...defaultInfos);
|
|
12038
|
-
for (const [routePrefix, backend] of Object.entries(this.routes)) {
|
|
12039
|
-
const infos = await backend.globInfo(pattern, "/");
|
|
12040
|
-
results.push(
|
|
12041
|
-
...infos.map((fi) => ({
|
|
12042
|
-
...fi,
|
|
12043
|
-
path: routePrefix.slice(0, -1) + fi.path
|
|
12044
|
-
}))
|
|
12045
|
-
);
|
|
12046
|
-
}
|
|
12047
|
-
results.sort((a, b) => a.path.localeCompare(b.path));
|
|
12048
|
-
return results;
|
|
12049
|
-
}
|
|
12050
|
-
/**
|
|
12051
|
-
* Create a new file, routing to appropriate backend.
|
|
12052
|
-
*
|
|
12053
|
-
* @param filePath - Absolute file path
|
|
12054
|
-
* @param content - File content as string
|
|
12055
|
-
* @returns WriteResult with path or error
|
|
12056
|
-
*/
|
|
12057
|
-
async write(filePath, content) {
|
|
12058
|
-
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
12059
|
-
return await backend.write(strippedKey, content);
|
|
12060
|
-
}
|
|
12061
|
-
/**
|
|
12062
|
-
* Edit a file, routing to appropriate backend.
|
|
12063
|
-
*
|
|
12064
|
-
* @param filePath - Absolute file path
|
|
12065
|
-
* @param oldString - String to find and replace
|
|
12066
|
-
* @param newString - Replacement string
|
|
12067
|
-
* @param replaceAll - If true, replace all occurrences
|
|
12068
|
-
* @returns EditResult with path, occurrences, or error
|
|
12069
|
-
*/
|
|
12070
|
-
async edit(filePath, oldString, newString, replaceAll = false) {
|
|
12071
|
-
const [backend, strippedKey] = this.getBackendAndKey(filePath);
|
|
12072
|
-
return await backend.edit(strippedKey, oldString, newString, replaceAll);
|
|
12073
|
-
}
|
|
12074
|
-
};
|
|
12075
|
-
|
|
12076
12126
|
// src/deep_agent_new/backends/memory.ts
|
|
12077
12127
|
var MemoryBackend = class {
|
|
12078
12128
|
constructor(files) {
|
|
@@ -12544,50 +12594,8 @@ ${BASE_PROMPT}` : BASE_PROMPT;
|
|
|
12544
12594
|
});
|
|
12545
12595
|
}
|
|
12546
12596
|
|
|
12547
|
-
// src/agent_lattice/builders/filesystemBackend.ts
|
|
12548
|
-
function createFilesystemBackendFactory(middlewareConfigs) {
|
|
12549
|
-
const filesystemConfig = middlewareConfigs.find((m) => m.type === "filesystem");
|
|
12550
|
-
if (!filesystemConfig || !filesystemConfig.enabled) {
|
|
12551
|
-
return void 0;
|
|
12552
|
-
}
|
|
12553
|
-
const isolatedLevel = filesystemConfig.config?.isolatedLevel || "global";
|
|
12554
|
-
return async (stateAndStore) => {
|
|
12555
|
-
const { tenantId, workspaceId, projectId } = stateAndStore;
|
|
12556
|
-
let sandboxName = "global";
|
|
12557
|
-
if (isolatedLevel === "agent") {
|
|
12558
|
-
sandboxName = "agent";
|
|
12559
|
-
} else if (isolatedLevel === "thread") {
|
|
12560
|
-
sandboxName = "thread";
|
|
12561
|
-
}
|
|
12562
|
-
const sandboxManager = sandboxLatticeManager.getSandboxLattice("default");
|
|
12563
|
-
if (!sandboxManager) {
|
|
12564
|
-
throw new Error("Sandbox manager not found");
|
|
12565
|
-
}
|
|
12566
|
-
let workingDirectory = "/";
|
|
12567
|
-
if (workspaceId && projectId) {
|
|
12568
|
-
if (tenantId) {
|
|
12569
|
-
workingDirectory = `/tenants/${tenantId}/workspaces/${workspaceId}/${projectId}`;
|
|
12570
|
-
} else {
|
|
12571
|
-
workingDirectory = `/workspaces/${workspaceId}/${projectId}`;
|
|
12572
|
-
}
|
|
12573
|
-
}
|
|
12574
|
-
const sandboxfs = new SandboxFilesystem({
|
|
12575
|
-
sandboxInstance: await sandboxManager.createSandbox(sandboxName),
|
|
12576
|
-
workingDirectory
|
|
12577
|
-
});
|
|
12578
|
-
const compositeBackend = new CompositeBackend(sandboxfs, {});
|
|
12579
|
-
return compositeBackend;
|
|
12580
|
-
};
|
|
12581
|
-
}
|
|
12582
|
-
|
|
12583
12597
|
// src/agent_lattice/builders/DeepAgentGraphBuilder.ts
|
|
12584
12598
|
var DeepAgentGraphBuilder = class {
|
|
12585
|
-
/**
|
|
12586
|
-
* 根据 middleware 配置创建 middlewares
|
|
12587
|
-
*/
|
|
12588
|
-
async createMiddlewares(middlewareConfigs) {
|
|
12589
|
-
return await createCommonMiddlewares(middlewareConfigs);
|
|
12590
|
-
}
|
|
12591
12599
|
/**
|
|
12592
12600
|
* 构建Deep Agent Graph
|
|
12593
12601
|
*
|
|
@@ -12622,7 +12630,7 @@ var DeepAgentGraphBuilder = class {
|
|
|
12622
12630
|
}));
|
|
12623
12631
|
const middlewareConfigs = params.middleware || [];
|
|
12624
12632
|
const filesystemBackend = createFilesystemBackendFactory(middlewareConfigs);
|
|
12625
|
-
const middlewares = await
|
|
12633
|
+
const middlewares = await createCommonMiddlewares(middlewareConfigs, filesystemBackend, true);
|
|
12626
12634
|
const deepAgent = createDeepAgent({
|
|
12627
12635
|
tools,
|
|
12628
12636
|
model: params.model,
|