@aiderdesk/aiderdesk 0.67.0 → 0.69.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/out/renderer/assets/{arc-BnPy4nhx.js → arc--tfU0Ahe.js} +1 -1
- package/out/renderer/assets/{architectureDiagram-3BPJPVTR-_SwpsbSs.js → architectureDiagram-3BPJPVTR-D2uDC6Pw.js} +3 -3
- package/out/renderer/assets/{blockDiagram-GPEHLZMM-D8Bc_xCY.js → blockDiagram-GPEHLZMM-BKopmU2x.js} +4 -4
- package/out/renderer/assets/{c4Diagram-AAUBKEIU-Ddic5IpI.js → c4Diagram-AAUBKEIU-CU9NH6bi.js} +2 -2
- package/out/renderer/assets/{channel-I2sEi2rW.js → channel-CBm2XBi8.js} +1 -1
- package/out/renderer/assets/{chunk-2J33WTMH-Cqrw7IHw.js → chunk-2J33WTMH-Yb07TKpF.js} +1 -1
- package/out/renderer/assets/{chunk-4BX2VUAB-DKY4go9E.js → chunk-4BX2VUAB-B1KgZMg1.js} +1 -1
- package/out/renderer/assets/{chunk-55IACEB6-COO6Gc0F.js → chunk-55IACEB6-BQ1g6F53.js} +1 -1
- package/out/renderer/assets/{chunk-727SXJPM-Bu8zhvGn.js → chunk-727SXJPM-nQzqwjgJ.js} +5 -5
- package/out/renderer/assets/{chunk-AQP2D5EJ-JHXEk1U1.js → chunk-AQP2D5EJ-8vVOUXUS.js} +3 -3
- package/out/renderer/assets/{chunk-FMBD7UC4-BqbYNISq.js → chunk-FMBD7UC4-dVquqYuV.js} +1 -1
- package/out/renderer/assets/{chunk-ND2GUHAM-D29ZgnDp.js → chunk-ND2GUHAM-Bu2VSodd.js} +1 -1
- package/out/renderer/assets/{chunk-QZHKN3VN-B-pbtAbR.js → chunk-QZHKN3VN-Bl58FmbX.js} +1 -1
- package/out/renderer/assets/{classDiagram-4FO5ZUOK-B7_tIdbP.js → classDiagram-4FO5ZUOK-Dmfohc7-.js} +6 -6
- package/out/renderer/assets/{classDiagram-v2-Q7XG4LA2-B7_tIdbP.js → classDiagram-v2-Q7XG4LA2-Dmfohc7-.js} +6 -6
- package/out/renderer/assets/{cose-bilkent-S5V4N54A-CGNgxRV6.js → cose-bilkent-S5V4N54A-8bgOaac3.js} +1 -1
- package/out/renderer/assets/{dagre-BM42HDAG-DB-tI7Ml.js → dagre-BM42HDAG-BZZ0JLHX.js} +3 -3
- package/out/renderer/assets/{diagram-2AECGRRQ-Cdwrgy7R.js → diagram-2AECGRRQ-9oArT1ZV.js} +3 -3
- package/out/renderer/assets/{diagram-5GNKFQAL-BnvZ78_N.js → diagram-5GNKFQAL-OMRICVmJ.js} +4 -4
- package/out/renderer/assets/{diagram-KO2AKTUF-VUrfwRCk.js → diagram-KO2AKTUF-pjPRIjL7.js} +3 -3
- package/out/renderer/assets/{diagram-LMA3HP47-_Vo8GrFC.js → diagram-LMA3HP47-cRVrdFbD.js} +3 -3
- package/out/renderer/assets/{diagram-OG6HWLK6-CoLz9kio.js → diagram-OG6HWLK6-gJvA5dOA.js} +4 -4
- package/out/renderer/assets/{erDiagram-TEJ5UH35-B3Bg3gW1.js → erDiagram-TEJ5UH35-BvHOuuhD.js} +4 -4
- package/out/renderer/assets/{flowDiagram-I6XJVG4X-BgyAk0Xe.js → flowDiagram-I6XJVG4X-D17Inzho.js} +6 -6
- package/out/renderer/assets/{ganttDiagram-6RSMTGT7-NnVRwQPs.js → ganttDiagram-6RSMTGT7-CIorTPIp.js} +1 -1
- package/out/renderer/assets/{gitGraphDiagram-PVQCEYII-C4vrRnDw.js → gitGraphDiagram-PVQCEYII-R3v9UanE.js} +4 -4
- package/out/renderer/assets/{graph-BZvTCUpv.js → graph-DNFReSa8.js} +1 -1
- package/out/renderer/assets/{index-P63PgYUG.js → index-COTYjomB.js} +28970 -133308
- package/out/renderer/assets/{index-zdiQSGqQ.css → index-D56aByCg.css} +40 -0
- package/out/renderer/assets/{infoDiagram-5YYISTIA-zTriWVJJ.js → infoDiagram-5YYISTIA-B4hJmlOG.js} +2 -2
- package/out/renderer/assets/{ishikawaDiagram-YF4QCWOH-DHO6Yeea.js → ishikawaDiagram-YF4QCWOH-DxohqJKP.js} +1 -1
- package/out/renderer/assets/{journeyDiagram-JHISSGLW-CZsRcg2X.js → journeyDiagram-JHISSGLW-BxFBZYTB.js} +4 -4
- package/out/renderer/assets/jsx-dev-runtime-BsbxiHH-.js +49 -0
- package/out/renderer/assets/{kanban-definition-UN3LZRKU-DSpAeh8p.js → kanban-definition-UN3LZRKU-B39Yt2kD.js} +2 -2
- package/out/renderer/assets/{layout-B5A8fT-Z.js → layout-yXTq0RED.js} +2 -2
- package/out/renderer/assets/{mindmap-definition-RKZ34NQL-Bns9Ab8p.js → mindmap-definition-RKZ34NQL-BD2OIaSH.js} +3 -3
- package/out/renderer/assets/{pieDiagram-4H26LBE5-BX36DY7W.js → pieDiagram-4H26LBE5-COAWItT4.js} +4 -4
- package/out/renderer/assets/pierre-dark-C-Drv5KU.js +4 -0
- package/out/renderer/assets/pierre-dark-soft-Cd74uQaL.js +4 -0
- package/out/renderer/assets/pierre-light-CfQnmt6J.js +4 -0
- package/out/renderer/assets/pierre-light-soft-DMVdU74b.js +4 -0
- package/out/renderer/assets/{quadrantDiagram-W4KKPZXB-DuD2qSni.js → quadrantDiagram-W4KKPZXB-BLY0H2F6.js} +1 -1
- package/out/renderer/assets/{requirementDiagram-4Y6WPE33-Th2uknlw.js → requirementDiagram-4Y6WPE33-DEJf5mz_.js} +3 -3
- package/out/renderer/assets/{sankeyDiagram-5OEKKPKP-DP3WODC7.js → sankeyDiagram-5OEKKPKP-D3BkTe8z.js} +1 -1
- package/out/renderer/assets/{sequenceDiagram-3UESZ5HK-BvpGEq-v.js → sequenceDiagram-3UESZ5HK-DUU_lUpD.js} +3 -3
- package/out/renderer/assets/{stateDiagram-AJRCARHV-Btrfma35.js → stateDiagram-AJRCARHV-DnH4p93i.js} +6 -6
- package/out/renderer/assets/{stateDiagram-v2-BHNVJYJU-v-8JiozM.js → stateDiagram-v2-BHNVJYJU-CRXRiP95.js} +4 -4
- package/out/renderer/assets/{timeline-definition-PNZ67QCA-prZy7cGx.js → timeline-definition-PNZ67QCA-Uv34KQP0.js} +2 -2
- package/out/renderer/assets/{vennDiagram-CIIHVFJN-XCVp5OjS.js → vennDiagram-CIIHVFJN-JyUQxmn1.js} +1 -1
- package/out/renderer/assets/{wardley-L42UT6IY-FZSNLjCs.js → wardley-L42UT6IY-4X2JoJpL.js} +1 -1
- package/out/renderer/assets/{wardleyDiagram-YWT4CUSO-Cla_7ryL.js → wardleyDiagram-YWT4CUSO-B9pIhVmY.js} +3 -3
- package/out/renderer/assets/{worker-CfJUABHG.js → worker-BdXuKH1Q.js} +274 -171
- package/out/renderer/assets/{xychartDiagram-2RQKCTM6-CKvwGbhk.js → xychartDiagram-2RQKCTM6-PJZgkel8.js} +1 -1
- package/out/renderer/index.html +2 -2
- package/out/resources/skills/extension-creator/SKILL.md +24 -0
- package/out/resources/skills/extension-creator/references/examples-gallery.md +11 -0
- package/out/resources/skills/extension-creator/references/extension-interface.md +4 -0
- package/out/resources/skills/extension-creator/references/external-libraries.md +159 -0
- package/out/resources/skills/extension-creator/references/ui-components.md +35 -0
- package/out/runner.js +546 -450
- package/package.json +20 -33
- package/patches/{ai+5.0.179.patch → ai+5.0.195.patch} +9 -9
- package/out/renderer/assets/pierre-dark-DADY5eR0.js +0 -4
- package/out/renderer/assets/pierre-light-DUjirxKp.js +0 -4
- package/patches/@ai-sdk+deepseek+1.0.37.patch +0 -150
- package/patches/ai-sdk-provider-claude-code+2.3.0.patch +0 -1024
package/out/runner.js
CHANGED
|
@@ -73,8 +73,6 @@ const clientBedrock = require("@aws-sdk/client-bedrock");
|
|
|
73
73
|
const credentialProviders = require("@aws-sdk/credential-providers");
|
|
74
74
|
const amazonBedrock = require("@ai-sdk/amazon-bedrock");
|
|
75
75
|
const cerebras = require("@ai-sdk/cerebras");
|
|
76
|
-
const aiSdkProviderClaudeCode = require("ai-sdk-provider-claude-code");
|
|
77
|
-
const jsonSchemaToZod = require("@dmitryrechkin/json-schema-to-zod");
|
|
78
76
|
const deepseek = require("@ai-sdk/deepseek");
|
|
79
77
|
const google = require("@ai-sdk/google");
|
|
80
78
|
const genai = require("@google/genai");
|
|
@@ -868,7 +866,6 @@ const CLOUDFLARED_BINARY_PATH = path.join(
|
|
|
868
866
|
"bin",
|
|
869
867
|
process.platform === "win32" ? "cloudflared.exe" : "cloudflared"
|
|
870
868
|
);
|
|
871
|
-
const CLAUDE_CODE_EXECUTABLE_PATH = path.join(RESOURCES_DIR, "app.asar.unpacked", "node_modules", "@anthropic-ai", "claude-agent-sdk", "cli.js");
|
|
872
869
|
const eventTransport = new EventTransport();
|
|
873
870
|
const logger = winston.createLogger({
|
|
874
871
|
level: process.env.LOG_LEVEL || "info",
|
|
@@ -1497,11 +1494,9 @@ const AVAILABLE_PROVIDERS = [
|
|
|
1497
1494
|
"alibaba-plan",
|
|
1498
1495
|
"anthropic",
|
|
1499
1496
|
"anthropic-compatible",
|
|
1500
|
-
"auggie",
|
|
1501
1497
|
"azure",
|
|
1502
1498
|
"bedrock",
|
|
1503
1499
|
"cerebras",
|
|
1504
|
-
"claude-agent-sdk",
|
|
1505
1500
|
"deepseek",
|
|
1506
1501
|
"gemini",
|
|
1507
1502
|
"gemini-cli",
|
|
@@ -1532,7 +1527,6 @@ const isOpenAiProvider = (provider) => provider.name === "openai";
|
|
|
1532
1527
|
const isAzureProvider = (provider) => provider.name === "azure";
|
|
1533
1528
|
const isAnthropicProvider = (provider) => provider.name === "anthropic";
|
|
1534
1529
|
const isAnthropicCompatibleProvider = (provider) => provider.name === "anthropic-compatible";
|
|
1535
|
-
const isAuggieProvider = (provider) => provider.name === "auggie";
|
|
1536
1530
|
const isKimiPlanProvider = (provider) => provider.name === "kimi-plan";
|
|
1537
1531
|
const isAlibabaPlanProvider = (provider) => provider.name === "alibaba-plan";
|
|
1538
1532
|
var GeminiVoiceModel = /* @__PURE__ */ ((GeminiVoiceModel2) => {
|
|
@@ -1545,7 +1539,6 @@ const isLmStudioProvider = (provider) => provider.name === "lmstudio";
|
|
|
1545
1539
|
const isDeepseekProvider = (provider) => provider.name === "deepseek";
|
|
1546
1540
|
const isGroqProvider = (provider) => provider.name === "groq";
|
|
1547
1541
|
const isCerebrasProvider = (provider) => provider.name === "cerebras";
|
|
1548
|
-
const isClaudeAgentSdkProvider = (provider) => provider.name === "claude-agent-sdk";
|
|
1549
1542
|
const isGeminiCliProvider = (provider) => provider.name === "gemini-cli";
|
|
1550
1543
|
const isBedrockProvider = (provider) => provider.name === "bedrock";
|
|
1551
1544
|
const isOpenAiCompatibleProvider = (provider) => provider.name === "openai-compatible";
|
|
@@ -1563,10 +1556,8 @@ const isSyntheticProvider = (provider) => provider.name === "synthetic";
|
|
|
1563
1556
|
const DEFAULT_PROVIDER_MODELS = {
|
|
1564
1557
|
"alibaba-plan": "qwen3-coder-plus",
|
|
1565
1558
|
anthropic: "claude-sonnet-4-6",
|
|
1566
|
-
auggie: "gpt-5-4",
|
|
1567
1559
|
bedrock: "global.anthropic.claude-sonnet-4-6",
|
|
1568
1560
|
cerebras: "qwen-3-235b-a22b-instruct-2507",
|
|
1569
|
-
"claude-agent-sdk": "sonnet",
|
|
1570
1561
|
deepseek: "deepseek-v4-pro",
|
|
1571
1562
|
gemini: "gemini-pro-latest",
|
|
1572
1563
|
"gemini-cli": "gemini-2.5-pro",
|
|
@@ -1639,6 +1630,7 @@ const DEFAULT_AGENT_PROFILE = {
|
|
|
1639
1630
|
useMemoryTools: true,
|
|
1640
1631
|
useSkillsTools: true,
|
|
1641
1632
|
useExtensionTools: true,
|
|
1633
|
+
disabledExtensionTools: [],
|
|
1642
1634
|
customInstructions: "",
|
|
1643
1635
|
enabledServers: [],
|
|
1644
1636
|
subagent: {
|
|
@@ -1774,6 +1766,7 @@ const COMPACT_CONVERSATION_AGENT_PROFILE = {
|
|
|
1774
1766
|
}
|
|
1775
1767
|
};
|
|
1776
1768
|
({
|
|
1769
|
+
...DEFAULT_AGENT_PROFILE,
|
|
1777
1770
|
toolApprovals: {
|
|
1778
1771
|
...DEFAULT_AGENT_PROFILE.toolApprovals,
|
|
1779
1772
|
[`${POWER_TOOL_GROUP_NAME}${TOOL_GROUP_NAME_SEPARATOR}${POWER_TOOL_FILE_EDIT}`]: ToolApprovalState.Never,
|
|
@@ -1823,13 +1816,6 @@ const getDefaultProviderParams = (providerName) => {
|
|
|
1823
1816
|
baseUrl: ""
|
|
1824
1817
|
};
|
|
1825
1818
|
break;
|
|
1826
|
-
case "auggie":
|
|
1827
|
-
provider = {
|
|
1828
|
-
name: "auggie",
|
|
1829
|
-
apiKey: "",
|
|
1830
|
-
apiUrl: ""
|
|
1831
|
-
};
|
|
1832
|
-
break;
|
|
1833
1819
|
case "gemini":
|
|
1834
1820
|
provider = {
|
|
1835
1821
|
name: "gemini",
|
|
@@ -2262,7 +2248,6 @@ const readApiKeyFromConfFile = (filePath, envVarName) => {
|
|
|
2262
2248
|
GOOGLE_API_KEY: ["gemini", "google"],
|
|
2263
2249
|
OPENAI_API_KEY: ["openai"],
|
|
2264
2250
|
ANTHROPIC_API_KEY: ["anthropic", "anthropic-compatible"],
|
|
2265
|
-
AUGMENT_API_TOKEN: ["auggie"],
|
|
2266
2251
|
GROQ_API_KEY: ["groq"],
|
|
2267
2252
|
ALIBABA_PLAN_API_KEY: ["alibaba-plan"],
|
|
2268
2253
|
KIMI_PLAN_API_KEY: ["kimi-plan"],
|
|
@@ -2446,6 +2431,19 @@ const getDefaultProjectSettings = (store, providerModels, baseDir, defaultAgentP
|
|
|
2446
2431
|
contextSidebarSectionsHidden: []
|
|
2447
2432
|
};
|
|
2448
2433
|
};
|
|
2434
|
+
const DEFAULT_FETCH_TIMEOUT_MS = 12e4;
|
|
2435
|
+
const fetchWithTimeout = async (url, timeoutMs = DEFAULT_FETCH_TIMEOUT_MS) => {
|
|
2436
|
+
const controller = new AbortController();
|
|
2437
|
+
const timeoutId = setTimeout(() => controller.abort(), timeoutMs);
|
|
2438
|
+
try {
|
|
2439
|
+
const response = await fetch(url, { signal: controller.signal });
|
|
2440
|
+
clearTimeout(timeoutId);
|
|
2441
|
+
return response;
|
|
2442
|
+
} catch (error) {
|
|
2443
|
+
clearTimeout(timeoutId);
|
|
2444
|
+
throw error;
|
|
2445
|
+
}
|
|
2446
|
+
};
|
|
2449
2447
|
const filenamify = filenamifyImport.default;
|
|
2450
2448
|
const getFilePathSuggestions = async (currentPath, directoriesOnly = false) => {
|
|
2451
2449
|
try {
|
|
@@ -3235,6 +3233,20 @@ const scrapeWeb = async (url, timeout = 6e4, abortSignal, format = "markdown") =
|
|
|
3235
3233
|
const scraper = new WebScraper();
|
|
3236
3234
|
return await scraper.scrape(url, timeout, abortSignal, format);
|
|
3237
3235
|
};
|
|
3236
|
+
const coerceBoolean = zod.z.preprocess((val) => {
|
|
3237
|
+
if (typeof val === "boolean") {
|
|
3238
|
+
return val;
|
|
3239
|
+
}
|
|
3240
|
+
if (typeof val === "string") {
|
|
3241
|
+
if (val.toLowerCase() === "true") {
|
|
3242
|
+
return true;
|
|
3243
|
+
}
|
|
3244
|
+
if (val.toLowerCase() === "false") {
|
|
3245
|
+
return false;
|
|
3246
|
+
}
|
|
3247
|
+
}
|
|
3248
|
+
return val;
|
|
3249
|
+
}, zod.z.boolean());
|
|
3238
3250
|
const THINKING_RESPONSE_STAR_TAG = "---\n► **THINKING**\n";
|
|
3239
3251
|
const ANSWER_RESPONSE_START_TAG = "---\n► **ANSWER**\n";
|
|
3240
3252
|
const extractPromptContextFromToolResult = (toolResult) => {
|
|
@@ -3471,8 +3483,8 @@ Include enough lines in each to uniquely match each set of lines that need to ch
|
|
|
3471
3483
|
Do not use escape characters \\ in the string like \\n or \\" and others. Do not start the search term with a \\ character.`
|
|
3472
3484
|
),
|
|
3473
3485
|
replacementText: zod.z.string().describe('The string to replace the searchTerm with. Do not use escape characters \\ in the string like \\n or \\" and others'),
|
|
3474
|
-
isRegex:
|
|
3475
|
-
replaceAll:
|
|
3486
|
+
isRegex: coerceBoolean.optional().default(false).describe("Whether the searchTerm should be treated as a regular expression. Use regex only when it is really needed. Default: false."),
|
|
3487
|
+
replaceAll: coerceBoolean.optional().default(false).describe("Whether to replace all occurrences or just the first one. Default: false.")
|
|
3476
3488
|
}),
|
|
3477
3489
|
execute: async (input, { toolCallId }) => {
|
|
3478
3490
|
const { filePath, searchTerm, replacementText, isRegex, replaceAll } = input;
|
|
@@ -3562,9 +3574,9 @@ Do not use escape characters \\ in the string like \\n or \\" and others. Do not
|
|
|
3562
3574
|
description: POWER_TOOL_DESCRIPTIONS[POWER_TOOL_FILE_READ],
|
|
3563
3575
|
inputSchema: zod.z.object({
|
|
3564
3576
|
filePath: zod.z.string().describe("The path to the file to be read (relative to the <WorkingDirectory> or absolute if outside of the directory)."),
|
|
3565
|
-
withLines:
|
|
3566
|
-
lineOffset: zod.z.number().int().min(0).optional().default(0).describe("The starting line number (0-based) to begin reading from. Default: 0."),
|
|
3567
|
-
lineLimit: zod.z.number().int().min(1).optional().default(1e3).describe("The maximum number of lines to read. Default: 1000.")
|
|
3577
|
+
withLines: coerceBoolean.optional().default(false).describe('Whether to return the file content with line numbers in format "lineNumber|content". Default: false.'),
|
|
3578
|
+
lineOffset: zod.z.coerce.number().int().min(0).optional().default(0).describe("The starting line number (0-based) to begin reading from. Default: 0."),
|
|
3579
|
+
lineLimit: zod.z.coerce.number().int().min(1).optional().default(1e3).describe("The maximum number of lines to read. Default: 1000.")
|
|
3568
3580
|
}),
|
|
3569
3581
|
execute: async (input, { toolCallId }) => {
|
|
3570
3582
|
const { filePath, withLines, lineOffset, lineLimit } = input;
|
|
@@ -3728,8 +3740,8 @@ Do not use escape characters \\ in the string like \\n or \\" and others. Do not
|
|
|
3728
3740
|
filePattern: zod.z.string().describe("A glob pattern specifying the files to search within (e.g., src/**/*.tsx, *.py)."),
|
|
3729
3741
|
searchTerm: zod.z.string().describe("The regular expression to search for within the files."),
|
|
3730
3742
|
contextLines: zod.z.number().int().min(0).optional().default(0).describe("The number of lines of context to show before and after each matching line. Default: 0."),
|
|
3731
|
-
caseSensitive:
|
|
3732
|
-
maxResults: zod.z.number().int().min(1).optional().default(50).describe("Maximum number of results to return. Default: 50.")
|
|
3743
|
+
caseSensitive: coerceBoolean.optional().default(false).describe("Whether the search should be case sensitive. Default: false."),
|
|
3744
|
+
maxResults: zod.z.coerce.number().int().min(1).optional().default(50).describe("Maximum number of results to return. Default: 50.")
|
|
3733
3745
|
}),
|
|
3734
3746
|
execute: async (input, { toolCallId }) => {
|
|
3735
3747
|
const { filePattern, searchTerm, contextLines, caseSensitive, maxResults } = input;
|
|
@@ -3896,7 +3908,7 @@ Do not use escape characters \\ in the string like \\n or \\" and others. Do not
|
|
|
3896
3908
|
inputSchema: zod.z.object({
|
|
3897
3909
|
command: zod.z.string().min(1).describe("The shell command to execute (e.g., ls -la, npm install)."),
|
|
3898
3910
|
cwd: zod.z.string().optional().describe("The working directory for the command (relative to <WorkingDirectory>). Default: <WorkingDirectory>."),
|
|
3899
|
-
timeout: zod.z.number().int().min(0).optional().default(12e4).describe("Timeout for the command execution in milliseconds. Default: 120000 ms.")
|
|
3911
|
+
timeout: zod.z.coerce.number().int().min(0).optional().default(12e4).describe("Timeout for the command execution in milliseconds. Default: 120000 ms.")
|
|
3900
3912
|
}),
|
|
3901
3913
|
execute: async (input, { toolCallId }) => {
|
|
3902
3914
|
const { command, cwd, timeout } = input;
|
|
@@ -4081,7 +4093,7 @@ Timeout: ${timeout}ms`;
|
|
|
4081
4093
|
description: POWER_TOOL_DESCRIPTIONS[POWER_TOOL_FETCH],
|
|
4082
4094
|
inputSchema: zod.z.object({
|
|
4083
4095
|
url: zod.z.string().describe("The URL to fetch."),
|
|
4084
|
-
timeout: zod.z.number().int().min(0).optional().default(6e4).describe("Timeout for the fetch operation in milliseconds. Default: 60000 ms."),
|
|
4096
|
+
timeout: zod.z.coerce.number().int().min(0).optional().default(6e4).describe("Timeout for the fetch operation in milliseconds. Default: 60000 ms."),
|
|
4085
4097
|
format: zod.z.enum(["markdown", "html", "raw"]).optional().default("markdown").describe(
|
|
4086
4098
|
'Format of the response: "markdown" (default, converts HTML to markdown), "html" (returns raw HTML), "raw" (fetches raw content via HTTP, ideal for API responses or raw files).'
|
|
4087
4099
|
)
|
|
@@ -4131,10 +4143,10 @@ Format: ${format}`;
|
|
|
4131
4143
|
inputSchema: zod.z.object({
|
|
4132
4144
|
query: zod.z.string().describe("Search query with Elasticsearch syntax. Use + for important terms."),
|
|
4133
4145
|
path: zod.z.string().optional().default(task.getTaskDir()).describe('Absolute path to search in. For dependencies use "go:github.com/owner/repo", "js:package_name", or "rust:cargo_name" etc.'),
|
|
4134
|
-
allowTests:
|
|
4135
|
-
exact:
|
|
4136
|
-
maxResults: zod.z.number().optional().describe("Maximum number of results to return"),
|
|
4137
|
-
maxTokens: zod.z.number().optional().default(5e3).describe("Maximum number of tokens to return"),
|
|
4146
|
+
allowTests: coerceBoolean.optional().default(false).describe("Allow test files in search results"),
|
|
4147
|
+
exact: coerceBoolean.optional().default(false).describe("Perform exact search without tokenization (case-insensitive)"),
|
|
4148
|
+
maxResults: zod.z.coerce.number().optional().describe("Maximum number of results to return"),
|
|
4149
|
+
maxTokens: zod.z.coerce.number().optional().default(5e3).describe("Maximum number of tokens to return"),
|
|
4138
4150
|
language: zod.z.string().optional().describe("Limit search to files of a specific programming language")
|
|
4139
4151
|
}),
|
|
4140
4152
|
execute: async (input, { toolCallId }) => {
|
|
@@ -4246,7 +4258,7 @@ const createTodoToolset = (task, profile, promptContext) => {
|
|
|
4246
4258
|
items: zod.z.array(
|
|
4247
4259
|
zod.z.object({
|
|
4248
4260
|
name: zod.z.string().describe("The name of the todo item."),
|
|
4249
|
-
completed:
|
|
4261
|
+
completed: coerceBoolean.optional().default(false).describe("Whether the todo item is completed.")
|
|
4250
4262
|
})
|
|
4251
4263
|
).describe("An array of todo items."),
|
|
4252
4264
|
initialUserPrompt: zod.z.string().describe("The original user prompt that initiated the task.")
|
|
@@ -4300,7 +4312,7 @@ Items: ${JSON.stringify(items)}`;
|
|
|
4300
4312
|
description: TODO_TOOL_DESCRIPTIONS[TODO_TOOL_UPDATE_ITEM_COMPLETION],
|
|
4301
4313
|
inputSchema: zod.z.object({
|
|
4302
4314
|
name: zod.z.string().describe("The name of the todo item to update."),
|
|
4303
|
-
completed:
|
|
4315
|
+
completed: coerceBoolean.describe("The new completion status for the todo item.")
|
|
4304
4316
|
}),
|
|
4305
4317
|
execute: async (input, { toolCallId }) => {
|
|
4306
4318
|
const { name, completed } = input;
|
|
@@ -4365,8 +4377,8 @@ const createTasksToolset = (settings, task, profile, promptContext) => {
|
|
|
4365
4377
|
const listTasksTool = ai.tool({
|
|
4366
4378
|
description: TASKS_TOOL_DESCRIPTIONS[TASKS_TOOL_LIST_TASKS],
|
|
4367
4379
|
inputSchema: zod.z.object({
|
|
4368
|
-
offset: zod.z.number().optional().describe("The number of tasks to skip (for pagination)"),
|
|
4369
|
-
limit: zod.z.number().optional().describe("The maximum number of tasks to return"),
|
|
4380
|
+
offset: zod.z.coerce.number().optional().describe("The number of tasks to skip (for pagination)"),
|
|
4381
|
+
limit: zod.z.coerce.number().optional().describe("The maximum number of tasks to return"),
|
|
4370
4382
|
state: zod.z.string().optional().describe("Filter tasks by state (e.g., TODO, IN_PROGRESS, DONE)")
|
|
4371
4383
|
}),
|
|
4372
4384
|
execute: async (input, { toolCallId }) => {
|
|
@@ -4530,7 +4542,7 @@ const createTasksToolset = (settings, task, profile, promptContext) => {
|
|
|
4530
4542
|
),
|
|
4531
4543
|
worktree: zod.z.boolean().optional().default(false).describe("If true, the task will be created in worktree mode. Use only when explicitly requested by the user."),
|
|
4532
4544
|
executeAndWait: zod.z.boolean().optional().default(false).describe("If true, the task will be created and executed immediately and the tool will wait for it to complete before returning."),
|
|
4533
|
-
executeInBackground:
|
|
4545
|
+
executeInBackground: coerceBoolean.optional().default(false).describe("If true, the task will be created and executed in the background.")
|
|
4534
4546
|
}),
|
|
4535
4547
|
execute: async (input, { toolCallId }) => {
|
|
4536
4548
|
const { prompt, name, agentProfileId, modelId, mode = "agent", asSubtask = false, autonomyMode, worktree, executeAndWait, executeInBackground } = input;
|
|
@@ -4694,7 +4706,7 @@ Prompt: ${prompt}${executeAndWait ? "\nWait for completion: true" : "\nRun in ba
|
|
|
4694
4706
|
inputSchema: zod.z.object({
|
|
4695
4707
|
taskId: zod.z.string().describe("The ID of the task to search within"),
|
|
4696
4708
|
query: zod.z.string().describe("Search query with Elasticsearch syntax. Use + for important terms."),
|
|
4697
|
-
maxTokens: zod.z.number().optional().default(1e4).describe("Maximum number of tokens to return in the search results. Default: 10000")
|
|
4709
|
+
maxTokens: zod.z.coerce.number().optional().default(1e4).describe("Maximum number of tokens to return in the search results. Default: 10000")
|
|
4698
4710
|
}),
|
|
4699
4711
|
execute: async (input, { toolCallId }) => {
|
|
4700
4712
|
const { taskId, query, maxTokens } = input;
|
|
@@ -4771,7 +4783,7 @@ const createSearchParentTaskTool = (task, promptContext) => {
|
|
|
4771
4783
|
description: TASKS_TOOL_DESCRIPTIONS[TASKS_TOOL_SEARCH_PARENT_TASK],
|
|
4772
4784
|
inputSchema: zod.z.object({
|
|
4773
4785
|
query: zod.z.string().describe("Search query with Elasticsearch syntax. Use + for important terms."),
|
|
4774
|
-
maxTokens: zod.z.number().optional().default(1e4).describe("Maximum number of tokens to return in the search results. Default: 10000")
|
|
4786
|
+
maxTokens: zod.z.coerce.number().optional().default(1e4).describe("Maximum number of tokens to return in the search results. Default: 10000")
|
|
4775
4787
|
}),
|
|
4776
4788
|
execute: async ({ query, maxTokens }, { toolCallId }) => {
|
|
4777
4789
|
const parentTaskId = task.task.parentId;
|
|
@@ -4861,7 +4873,7 @@ const createAiderToolset = (task, profile, promptContext) => {
|
|
|
4861
4873
|
description: AIDER_TOOL_DESCRIPTIONS[AIDER_TOOL_ADD_CONTEXT_FILES],
|
|
4862
4874
|
inputSchema: zod.z.object({
|
|
4863
4875
|
paths: zod.z.array(zod.z.string()).describe('One or more file paths to add to context. Relative to task directory (e.g. "src/file.ts") or absolute (e.g. "/tmp/log.txt" for read-only).'),
|
|
4864
|
-
readOnly:
|
|
4876
|
+
readOnly: coerceBoolean.optional().describe("Whether the file(s) are read-only. Applies to all paths if true.")
|
|
4865
4877
|
}),
|
|
4866
4878
|
execute: async (input, { toolCallId }) => {
|
|
4867
4879
|
const { paths, readOnly = false } = input;
|
|
@@ -5090,7 +5102,7 @@ const createMemoryToolset = (task, profile, memoryManager, promptContext) => {
|
|
|
5090
5102
|
description: MEMORY_TOOL_DESCRIPTIONS[MEMORY_TOOL_RETRIEVE],
|
|
5091
5103
|
inputSchema: zod.z.object({
|
|
5092
5104
|
query: zod.z.string().describe("The search query to find relevant memories"),
|
|
5093
|
-
limit: zod.z.number().optional().default(3).describe("Maximum number of memories to retrieve (default: 3)")
|
|
5105
|
+
limit: zod.z.coerce.number().optional().default(3).describe("Maximum number of memories to retrieve (default: 3)")
|
|
5094
5106
|
}),
|
|
5095
5107
|
execute: async (input, { toolCallId }) => {
|
|
5096
5108
|
const { query, limit } = input;
|
|
@@ -5157,7 +5169,7 @@ Timestamp: ${new Date(memory.timestamp).toLocaleString()}`;
|
|
|
5157
5169
|
description: MEMORY_TOOL_DESCRIPTIONS[MEMORY_TOOL_LIST],
|
|
5158
5170
|
inputSchema: zod.z.object({
|
|
5159
5171
|
type: zod.z.enum(["task", "user-preference", "code-pattern"]).optional().describe("Filter by memory type"),
|
|
5160
|
-
limit: zod.z.number().optional().default(20).describe("Maximum number of memories to list (default: 20)")
|
|
5172
|
+
limit: zod.z.coerce.number().optional().default(20).describe("Maximum number of memories to list (default: 20)")
|
|
5161
5173
|
}),
|
|
5162
5174
|
execute: async (input, { toolCallId }) => {
|
|
5163
5175
|
const { type, limit } = input;
|
|
@@ -6581,14 +6593,16 @@ ${file.content}</content-with-line-numbers>
|
|
|
6581
6593
|
logger.debug("Adding file list for non-image files", {
|
|
6582
6594
|
files: nonImageFiles.map((f) => f.path)
|
|
6583
6595
|
});
|
|
6596
|
+
const hasReadOnlyFiles = nonImageFiles.some((file) => file.readOnly);
|
|
6584
6597
|
const fileList = nonImageFiles.map((file) => {
|
|
6585
|
-
return `- ${file.path}`;
|
|
6598
|
+
return `- ${file.path}${file.readOnly ? " (read-only)" : ""}`;
|
|
6586
6599
|
}).join("\n");
|
|
6600
|
+
const readOnlyNote = hasReadOnlyFiles ? "\n\nNote: Files marked as read-only must NOT be modified. Use them only for understanding context." : "";
|
|
6587
6601
|
messages.push({
|
|
6588
6602
|
role: "user",
|
|
6589
6603
|
content: `The following files are currently in the working context:
|
|
6590
6604
|
|
|
6591
|
-
${fileList}`
|
|
6605
|
+
${fileList}${readOnlyNote}`
|
|
6592
6606
|
});
|
|
6593
6607
|
messages.push({
|
|
6594
6608
|
role: "assistant",
|
|
@@ -6686,7 +6700,7 @@ ${fileList}`
|
|
|
6686
6700
|
const providerTools = await this.modelManager.getProviderTools(provider, model);
|
|
6687
6701
|
Object.assign(toolSet, providerTools);
|
|
6688
6702
|
if (this.extensionManager.isInitialized() && profile.useExtensionTools !== false) {
|
|
6689
|
-
const extensionTools = this.extensionManager.createExtensionToolset(task, mode, profile, toolSet, abortSignal);
|
|
6703
|
+
const extensionTools = this.extensionManager.createExtensionToolset(task, mode, profile, toolSet, approvalManager, abortSignal);
|
|
6690
6704
|
Object.assign(toolSet, extensionTools);
|
|
6691
6705
|
}
|
|
6692
6706
|
return this.wrapToolsWithHooks(task, profile, toolSet, abortSignal, promptContext);
|
|
@@ -6702,7 +6716,7 @@ ${fileList}`
|
|
|
6702
6716
|
task.addToolMessage(options.toolCallId, serverName, messageToolName, effectiveInput, void 0, void 0, promptContext);
|
|
6703
6717
|
const toolCalledExtensionResult = await this.extensionManager.dispatchEvent(
|
|
6704
6718
|
"onToolCalled",
|
|
6705
|
-
{ toolName, agentProfile: profile, input: effectiveInput, abortSignal: options.abortSignal || abortSignal },
|
|
6719
|
+
{ toolCallId: options.toolCallId, toolName, agentProfile: profile, input: effectiveInput, abortSignal: options.abortSignal || abortSignal },
|
|
6706
6720
|
task.project,
|
|
6707
6721
|
task
|
|
6708
6722
|
);
|
|
@@ -6719,7 +6733,7 @@ ${fileList}`
|
|
|
6719
6733
|
}
|
|
6720
6734
|
const toolFinishedExtensionResult = await this.extensionManager.dispatchEvent(
|
|
6721
6735
|
"onToolFinished",
|
|
6722
|
-
{ toolName, agentProfile: profile, input: effectiveInput, output: result },
|
|
6736
|
+
{ toolCallId: options.toolCallId, toolName, agentProfile: profile, input: effectiveInput, output: result },
|
|
6723
6737
|
task.project,
|
|
6724
6738
|
task
|
|
6725
6739
|
);
|
|
@@ -7838,7 +7852,7 @@ ${fileList}`
|
|
|
7838
7852
|
const processToolResult = (toolResult) => {
|
|
7839
7853
|
const [serverName, toolName] = extractServerNameToolName(toolResult.toolName);
|
|
7840
7854
|
const toolPromptContext = extractPromptContextFromToolResult(toolResult.output) ?? promptContext;
|
|
7841
|
-
task.addToolMessage(toolResult.toolCallId, serverName, toolName, toolResult.input, JSON.stringify(toolResult.output),
|
|
7855
|
+
task.addToolMessage(toolResult.toolCallId, serverName, toolName, toolResult.input, JSON.stringify(toolResult.output), usageReport, toolPromptContext);
|
|
7842
7856
|
};
|
|
7843
7857
|
for (let i = 0; i < content.length; i++) {
|
|
7844
7858
|
let part = content[i];
|
|
@@ -8324,6 +8338,7 @@ class AgentProfileManager {
|
|
|
8324
8338
|
maxIterations: loadedProfile.maxIterations ?? DEFAULT_AGENT_PROFILE.maxIterations,
|
|
8325
8339
|
minTimeBetweenToolCalls: loadedProfile.minTimeBetweenToolCalls ?? DEFAULT_AGENT_PROFILE.minTimeBetweenToolCalls,
|
|
8326
8340
|
enabledServers: loadedProfile.enabledServers ?? [],
|
|
8341
|
+
disabledExtensionTools: loadedProfile.disabledExtensionTools ?? [],
|
|
8327
8342
|
customInstructions: loadedProfile.customInstructions ?? "",
|
|
8328
8343
|
toolApprovals: {
|
|
8329
8344
|
...loadedProfile.toolApprovals
|
|
@@ -9293,11 +9308,22 @@ const MergeWorktreeToMainSchema = zod.z.object({
|
|
|
9293
9308
|
targetBranch: zod.z.string().optional(),
|
|
9294
9309
|
commitMessage: zod.z.string().optional()
|
|
9295
9310
|
});
|
|
9296
|
-
const
|
|
9311
|
+
const SwitchToLocalWorkingModeSchema = zod.z.object({
|
|
9297
9312
|
projectDir: zod.z.string().min(1, "Project directory is required"),
|
|
9298
9313
|
taskId: zod.z.string().min(1, "Task id is required"),
|
|
9314
|
+
mergeBeforeSwitch: zod.z.boolean().optional(),
|
|
9299
9315
|
targetBranch: zod.z.string().optional()
|
|
9300
9316
|
});
|
|
9317
|
+
const SwitchToWorktreeWorkingModeSchema = zod.z.object({
|
|
9318
|
+
projectDir: zod.z.string().min(1, "Project directory is required"),
|
|
9319
|
+
taskId: zod.z.string().min(1, "Task id is required"),
|
|
9320
|
+
carryOverUncommittedChanges: zod.z.boolean().optional(),
|
|
9321
|
+
dropSourceChanges: zod.z.boolean().optional()
|
|
9322
|
+
});
|
|
9323
|
+
const LocalUncommittedFilesSchema = zod.z.object({
|
|
9324
|
+
projectDir: zod.z.string().min(1, "Project directory is required"),
|
|
9325
|
+
taskId: zod.z.string().min(1, "Task id is required")
|
|
9326
|
+
});
|
|
9301
9327
|
const ApplyUncommittedChangesSchema = zod.z.object({
|
|
9302
9328
|
projectDir: zod.z.string().min(1, "Project directory is required"),
|
|
9303
9329
|
taskId: zod.z.string().min(1, "Task id is required"),
|
|
@@ -9748,15 +9774,39 @@ class ProjectApi extends BaseApi {
|
|
|
9748
9774
|
})
|
|
9749
9775
|
);
|
|
9750
9776
|
router.post(
|
|
9751
|
-
"/project/
|
|
9777
|
+
"/project/switch-to-local-working-mode",
|
|
9752
9778
|
this.handleRequest(async (req, res) => {
|
|
9753
|
-
const parsed = this.validateRequest(
|
|
9779
|
+
const parsed = this.validateRequest(SwitchToLocalWorkingModeSchema, req.body, res);
|
|
9754
9780
|
if (!parsed) {
|
|
9755
9781
|
return;
|
|
9756
9782
|
}
|
|
9757
|
-
const { projectDir, taskId, targetBranch } = parsed;
|
|
9758
|
-
await this.eventsHandler.
|
|
9759
|
-
res.status(200).json({ message: "
|
|
9783
|
+
const { projectDir, taskId, mergeBeforeSwitch, targetBranch } = parsed;
|
|
9784
|
+
await this.eventsHandler.switchToLocalWorkingMode(projectDir, taskId, { mergeBeforeSwitch, targetBranch });
|
|
9785
|
+
res.status(200).json({ message: "Switched to local working mode" });
|
|
9786
|
+
})
|
|
9787
|
+
);
|
|
9788
|
+
router.post(
|
|
9789
|
+
"/project/switch-to-worktree-working-mode",
|
|
9790
|
+
this.handleRequest(async (req, res) => {
|
|
9791
|
+
const parsed = this.validateRequest(SwitchToWorktreeWorkingModeSchema, req.body, res);
|
|
9792
|
+
if (!parsed) {
|
|
9793
|
+
return;
|
|
9794
|
+
}
|
|
9795
|
+
const { projectDir, taskId, carryOverUncommittedChanges, dropSourceChanges } = parsed;
|
|
9796
|
+
await this.eventsHandler.switchToWorktreeWorkingMode(projectDir, taskId, { carryOverUncommittedChanges, dropSourceChanges });
|
|
9797
|
+
res.status(200).json({ message: "Switched to worktree working mode" });
|
|
9798
|
+
})
|
|
9799
|
+
);
|
|
9800
|
+
router.get(
|
|
9801
|
+
"/project/local-uncommitted-files",
|
|
9802
|
+
this.handleRequest(async (req, res) => {
|
|
9803
|
+
const parsed = this.validateRequest(LocalUncommittedFilesSchema, req.query, res);
|
|
9804
|
+
if (!parsed) {
|
|
9805
|
+
return;
|
|
9806
|
+
}
|
|
9807
|
+
const { projectDir, taskId } = parsed;
|
|
9808
|
+
const result = await this.eventsHandler.getLocalUncommittedFiles(projectDir, taskId);
|
|
9809
|
+
res.status(200).json(result);
|
|
9760
9810
|
})
|
|
9761
9811
|
);
|
|
9762
9812
|
router.post(
|
|
@@ -10700,6 +10750,9 @@ class TerminalApi extends BaseApi {
|
|
|
10700
10750
|
const GetInstalledExtensionsSchema = zod.z.object({
|
|
10701
10751
|
projectDir: zod.z.string().optional()
|
|
10702
10752
|
});
|
|
10753
|
+
const GetExtensionToolsInfoSchema = zod.z.object({
|
|
10754
|
+
projectDir: zod.z.string().optional()
|
|
10755
|
+
});
|
|
10703
10756
|
const GetAvailableExtensionsSchema = zod.z.object({
|
|
10704
10757
|
repositories: zod.z.string().optional(),
|
|
10705
10758
|
// Comma-separated URLs
|
|
@@ -10738,6 +10791,18 @@ class ExtensionsApi extends BaseApi {
|
|
|
10738
10791
|
res.status(200).json(extensions);
|
|
10739
10792
|
})
|
|
10740
10793
|
);
|
|
10794
|
+
router.get(
|
|
10795
|
+
"/extensions/tools-info",
|
|
10796
|
+
this.handleRequest(async (req, res) => {
|
|
10797
|
+
const parsed = this.validateRequest(GetExtensionToolsInfoSchema, req.query, res);
|
|
10798
|
+
if (!parsed) {
|
|
10799
|
+
return;
|
|
10800
|
+
}
|
|
10801
|
+
const { projectDir } = parsed;
|
|
10802
|
+
const toolsInfo = this.eventsHandler.getExtensionToolsInfo(projectDir);
|
|
10803
|
+
res.status(200).json(toolsInfo);
|
|
10804
|
+
})
|
|
10805
|
+
);
|
|
10741
10806
|
router.get(
|
|
10742
10807
|
"/extensions/available",
|
|
10743
10808
|
this.handleRequest(async (req, res) => {
|
|
@@ -10830,6 +10895,18 @@ class ExtensionsApi extends BaseApi {
|
|
|
10830
10895
|
res.status(200).json(result);
|
|
10831
10896
|
})
|
|
10832
10897
|
);
|
|
10898
|
+
router.post(
|
|
10899
|
+
"/extensions/load-library",
|
|
10900
|
+
this.handleRequest(async (req, res) => {
|
|
10901
|
+
const { librarySpec } = req.body;
|
|
10902
|
+
if (!librarySpec) {
|
|
10903
|
+
res.status(400).json({ message: "librarySpec is required" });
|
|
10904
|
+
return;
|
|
10905
|
+
}
|
|
10906
|
+
const source = await this.eventsHandler.loadExtensionLibrary(librarySpec);
|
|
10907
|
+
res.status(200).type("application/javascript").send(source);
|
|
10908
|
+
})
|
|
10909
|
+
);
|
|
10833
10910
|
router.get(
|
|
10834
10911
|
"/extensions/config-component",
|
|
10835
10912
|
this.handleRequest(async (req, res) => {
|
|
@@ -12604,6 +12681,7 @@ ${JSON.stringify(part.output.value)}`
|
|
|
12604
12681
|
toolMessage.response = JSON.stringify(part.output.value);
|
|
12605
12682
|
toolMessage.usageReport = message.usageReport || toolMessage.usageReport;
|
|
12606
12683
|
toolMessage.promptContext = promptContext;
|
|
12684
|
+
toolMessage.finished = true;
|
|
12607
12685
|
}
|
|
12608
12686
|
if (serverName === AIDER_TOOL_GROUP_NAME && toolName === AIDER_TOOL_RUN_PROMPT && part.output?.value && typeof part.output.value === "object" && "responses" in part.output.value) {
|
|
12609
12687
|
const responses = part.output.value.responses;
|
|
@@ -12704,6 +12782,7 @@ ${JSON.stringify(part.output.value)}`
|
|
|
12704
12782
|
const toolMessage2 = messagesData.find((message2) => message2.type === "tool" && message2.id === subPart.toolCallId);
|
|
12705
12783
|
if (toolMessage2) {
|
|
12706
12784
|
toolMessage2.response = JSON.stringify(subPart.output.value);
|
|
12785
|
+
toolMessage2.finished = true;
|
|
12707
12786
|
}
|
|
12708
12787
|
}
|
|
12709
12788
|
}
|
|
@@ -12783,6 +12862,7 @@ ${JSON.stringify(part.output.value)}`
|
|
|
12783
12862
|
if (toolMessage) {
|
|
12784
12863
|
toolMessage.response = JSON.stringify(toolResultData.output);
|
|
12785
12864
|
toolMessage.usageReport = message.usageReport || toolMessage.usageReport;
|
|
12865
|
+
toolMessage.finished = true;
|
|
12786
12866
|
const promptContext = extractPromptContextFromToolResult(toolResultData.output);
|
|
12787
12867
|
if (promptContext) {
|
|
12788
12868
|
toolMessage.promptContext = promptContext;
|
|
@@ -15405,6 +15485,12 @@ Git output: ${err.stderr || err.stdout || err.message}`
|
|
|
15405
15485
|
await this.pruneDeleted(projectDir);
|
|
15406
15486
|
}
|
|
15407
15487
|
}
|
|
15488
|
+
var CompactionLevel = /* @__PURE__ */ ((CompactionLevel2) => {
|
|
15489
|
+
CompactionLevel2[CompactionLevel2["One"] = 1] = "One";
|
|
15490
|
+
CompactionLevel2[CompactionLevel2["Two"] = 2] = "Two";
|
|
15491
|
+
CompactionLevel2[CompactionLevel2["Three"] = 3] = "Three";
|
|
15492
|
+
return CompactionLevel2;
|
|
15493
|
+
})(CompactionLevel || {});
|
|
15408
15494
|
const extractFilePath = (args) => {
|
|
15409
15495
|
if (typeof args === "object" && args !== null && "filePath" in args) {
|
|
15410
15496
|
return args.filePath;
|
|
@@ -15545,8 +15631,9 @@ const mergeConsecutiveAssistantMessages = (messages) => {
|
|
|
15545
15631
|
return true;
|
|
15546
15632
|
});
|
|
15547
15633
|
};
|
|
15548
|
-
const truncateNonPowerToolResults = async (messages, protectedMessageCount = 10) => {
|
|
15634
|
+
const truncateNonPowerToolResults = async (messages, protectedMessageCount = 10, compactionLevel = 1) => {
|
|
15549
15635
|
const protectedStart = getProtectedStartIndex(messages, protectedMessageCount);
|
|
15636
|
+
const redactionMessage = "Result redacted due to compaction, run again if needed.";
|
|
15550
15637
|
for (let i = 0; i < protectedStart; i++) {
|
|
15551
15638
|
const msg = messages[i];
|
|
15552
15639
|
if (msg.role !== "tool") {
|
|
@@ -15561,6 +15648,20 @@ const truncateNonPowerToolResults = async (messages, protectedMessageCount = 10)
|
|
|
15561
15648
|
if (isPowerTool(serverName)) {
|
|
15562
15649
|
continue;
|
|
15563
15650
|
}
|
|
15651
|
+
if (compactionLevel >= 3) {
|
|
15652
|
+
if (part.output.type === "text" || part.output.type === "error-text") {
|
|
15653
|
+
part.output = {
|
|
15654
|
+
type: part.output.type,
|
|
15655
|
+
value: redactionMessage
|
|
15656
|
+
};
|
|
15657
|
+
} else {
|
|
15658
|
+
part.output = {
|
|
15659
|
+
type: "text",
|
|
15660
|
+
value: redactionMessage
|
|
15661
|
+
};
|
|
15662
|
+
}
|
|
15663
|
+
continue;
|
|
15664
|
+
}
|
|
15564
15665
|
if (part.output.type !== "text" && part.output.type !== "error-text") {
|
|
15565
15666
|
continue;
|
|
15566
15667
|
}
|
|
@@ -15568,11 +15669,14 @@ const truncateNonPowerToolResults = async (messages, protectedMessageCount = 10)
|
|
|
15568
15669
|
if (!outputText) {
|
|
15569
15670
|
continue;
|
|
15570
15671
|
}
|
|
15672
|
+
const maxLines = compactionLevel >= 2 ? 10 : 20;
|
|
15673
|
+
const maxSizeKB = compactionLevel >= 2 ? 1 : 2;
|
|
15674
|
+
const maxTokens = compactionLevel >= 2 ? 1e3 : 2e3;
|
|
15571
15675
|
const truncated = await truncateToolResult(
|
|
15572
15676
|
outputText,
|
|
15573
|
-
|
|
15574
|
-
|
|
15575
|
-
|
|
15677
|
+
maxLines,
|
|
15678
|
+
maxSizeKB,
|
|
15679
|
+
maxTokens,
|
|
15576
15680
|
false,
|
|
15577
15681
|
"Output truncated due to compaction, re-execute the tool if full output is needed."
|
|
15578
15682
|
);
|
|
@@ -15586,17 +15690,17 @@ const truncateNonPowerToolResults = async (messages, protectedMessageCount = 10)
|
|
|
15586
15690
|
}
|
|
15587
15691
|
return messages;
|
|
15588
15692
|
};
|
|
15589
|
-
const smartCompactMessages = async (messages, protectedMessageCount = 10) => {
|
|
15693
|
+
const smartCompactMessages = async (messages, protectedMessageCount = 10, compactionLevel = 1) => {
|
|
15590
15694
|
let result = cloneMessages(messages);
|
|
15591
15695
|
result = removeErroredTools(result, protectedMessageCount);
|
|
15592
15696
|
result = collapseFileEdits(result, protectedMessageCount);
|
|
15593
15697
|
result = removeStaleFileReads(result, protectedMessageCount);
|
|
15594
|
-
result = compactFileReads(result, protectedMessageCount);
|
|
15595
|
-
result = removeObsoleteSearches(result, protectedMessageCount);
|
|
15596
|
-
result = compactSemanticSearches(result, protectedMessageCount);
|
|
15597
|
-
result =
|
|
15698
|
+
result = compactFileReads(result, protectedMessageCount, compactionLevel);
|
|
15699
|
+
result = removeObsoleteSearches(result, protectedMessageCount, compactionLevel);
|
|
15700
|
+
result = compactSemanticSearches(result, protectedMessageCount, compactionLevel);
|
|
15701
|
+
result = compactBashOutputs(result, protectedMessageCount, compactionLevel);
|
|
15598
15702
|
result = redactFetchOutputs(result, protectedMessageCount);
|
|
15599
|
-
result = await truncateNonPowerToolResults(result, protectedMessageCount);
|
|
15703
|
+
result = await truncateNonPowerToolResults(result, protectedMessageCount, compactionLevel);
|
|
15600
15704
|
result = mergeConsecutiveAssistantMessages(result);
|
|
15601
15705
|
return result;
|
|
15602
15706
|
};
|
|
@@ -15800,8 +15904,9 @@ const removeStaleFileReads = (messages, protectedMessageCount = 10) => {
|
|
|
15800
15904
|
}
|
|
15801
15905
|
return messages;
|
|
15802
15906
|
};
|
|
15803
|
-
const compactFileReads = (messages, protectedMessageCount = 10) => {
|
|
15907
|
+
const compactFileReads = (messages, protectedMessageCount = 10, compactionLevel = 1) => {
|
|
15804
15908
|
const protectedStart = getProtectedStartIndex(messages, protectedMessageCount);
|
|
15909
|
+
const maxLines = compactionLevel === 3 ? 0 : compactionLevel === 2 ? 20 : 50;
|
|
15805
15910
|
for (let i = 0; i < protectedStart; i++) {
|
|
15806
15911
|
if (i >= messages.length) {
|
|
15807
15912
|
break;
|
|
@@ -15822,18 +15927,25 @@ const compactFileReads = (messages, protectedMessageCount = 10) => {
|
|
|
15822
15927
|
if (part.output.type !== "text") {
|
|
15823
15928
|
continue;
|
|
15824
15929
|
}
|
|
15930
|
+
if (compactionLevel === 3) {
|
|
15931
|
+
part.output = {
|
|
15932
|
+
type: "text",
|
|
15933
|
+
value: "<result redacted due to compaction, read the file again if content is needed>"
|
|
15934
|
+
};
|
|
15935
|
+
continue;
|
|
15936
|
+
}
|
|
15825
15937
|
const lines = part.output.value.split("\n");
|
|
15826
|
-
if (lines.length >
|
|
15938
|
+
if (lines.length > maxLines) {
|
|
15827
15939
|
part.output = {
|
|
15828
15940
|
type: "text",
|
|
15829
|
-
value: lines.slice(0,
|
|
15941
|
+
value: lines.slice(0, maxLines).join("\n") + "\n<truncated due to compaction, read the file again if full content is needed>"
|
|
15830
15942
|
};
|
|
15831
15943
|
}
|
|
15832
15944
|
}
|
|
15833
15945
|
}
|
|
15834
15946
|
return messages;
|
|
15835
15947
|
};
|
|
15836
|
-
const removeObsoleteSearches = (messages, protectedMessageCount = 10) => {
|
|
15948
|
+
const removeObsoleteSearches = (messages, protectedMessageCount = 10, compactionLevel = 1) => {
|
|
15837
15949
|
const protectedStart = getProtectedStartIndex(messages, protectedMessageCount);
|
|
15838
15950
|
const fileModificationPositions = [];
|
|
15839
15951
|
for (let i = 0; i < messages.length; i++) {
|
|
@@ -15864,7 +15976,7 @@ const removeObsoleteSearches = (messages, protectedMessageCount = 10) => {
|
|
|
15864
15976
|
}
|
|
15865
15977
|
}
|
|
15866
15978
|
const hasFileModifications = fileModificationPositions.length > 0;
|
|
15867
|
-
if (!hasFileModifications) {
|
|
15979
|
+
if (!hasFileModifications && compactionLevel < 3) {
|
|
15868
15980
|
return messages;
|
|
15869
15981
|
}
|
|
15870
15982
|
for (let i = protectedStart - 1; i >= 0; i--) {
|
|
@@ -15886,8 +15998,8 @@ const removeObsoleteSearches = (messages, protectedMessageCount = 10) => {
|
|
|
15886
15998
|
if (toolName !== POWER_TOOL_GLOB && toolName !== POWER_TOOL_GREP) {
|
|
15887
15999
|
continue;
|
|
15888
16000
|
}
|
|
15889
|
-
const
|
|
15890
|
-
if (
|
|
16001
|
+
const shouldRemove = compactionLevel >= 3 || fileModificationPositions.some((pos) => pos > i);
|
|
16002
|
+
if (shouldRemove) {
|
|
15891
16003
|
removeToolCallFromAssistant(messages, part.toolCallId);
|
|
15892
16004
|
removeToolResult(messages, part.toolCallId);
|
|
15893
16005
|
}
|
|
@@ -15895,7 +16007,7 @@ const removeObsoleteSearches = (messages, protectedMessageCount = 10) => {
|
|
|
15895
16007
|
}
|
|
15896
16008
|
return messages;
|
|
15897
16009
|
};
|
|
15898
|
-
const compactSemanticSearches = (messages, protectedMessageCount = 10) => {
|
|
16010
|
+
const compactSemanticSearches = (messages, protectedMessageCount = 10, compactionLevel = 1) => {
|
|
15899
16011
|
const protectedStart = getProtectedStartIndex(messages, protectedMessageCount);
|
|
15900
16012
|
const searchIndices = [];
|
|
15901
16013
|
for (let i = 0; i < protectedStart; i++) {
|
|
@@ -15918,7 +16030,14 @@ const compactSemanticSearches = (messages, protectedMessageCount = 10) => {
|
|
|
15918
16030
|
searchIndices.push({ messageIndex: i, partIndex: j, toolCallId: part.toolCallId });
|
|
15919
16031
|
}
|
|
15920
16032
|
}
|
|
15921
|
-
if (searchIndices.length <= 1) {
|
|
16033
|
+
if (searchIndices.length <= 1 && compactionLevel < 3) {
|
|
16034
|
+
return messages;
|
|
16035
|
+
}
|
|
16036
|
+
if (compactionLevel >= 3) {
|
|
16037
|
+
for (const search2 of searchIndices) {
|
|
16038
|
+
removeToolCallFromAssistant(messages, search2.toolCallId);
|
|
16039
|
+
removeToolResult(messages, search2.toolCallId);
|
|
16040
|
+
}
|
|
15922
16041
|
return messages;
|
|
15923
16042
|
}
|
|
15924
16043
|
const toRemove = searchIndices.slice(0, -1);
|
|
@@ -15927,6 +16046,7 @@ const compactSemanticSearches = (messages, protectedMessageCount = 10) => {
|
|
|
15927
16046
|
removeToolCallFromAssistant(messages, search2.toolCallId);
|
|
15928
16047
|
removeToolResult(messages, search2.toolCallId);
|
|
15929
16048
|
}
|
|
16049
|
+
const maxLines = compactionLevel === 2 ? 20 : 50;
|
|
15930
16050
|
const keptToolIdx = messages.findIndex((m) => m.role === "tool" && m.content.some((p) => p.type === "tool-result" && p.toolCallId === toKeep.toolCallId));
|
|
15931
16051
|
if (keptToolIdx !== -1) {
|
|
15932
16052
|
const keptMsg = messages[keptToolIdx];
|
|
@@ -15934,18 +16054,19 @@ const compactSemanticSearches = (messages, protectedMessageCount = 10) => {
|
|
|
15934
16054
|
const keptPart = keptMsg.content[keptPartIdx];
|
|
15935
16055
|
if (keptPart && keptPart.output.type === "text") {
|
|
15936
16056
|
const lines = keptPart.output.value.split("\n");
|
|
15937
|
-
if (lines.length >
|
|
16057
|
+
if (lines.length > maxLines) {
|
|
15938
16058
|
keptPart.output = {
|
|
15939
16059
|
type: "text",
|
|
15940
|
-
value: lines.slice(0,
|
|
16060
|
+
value: lines.slice(0, maxLines).join("\n") + "\n<truncated due to compaction, run again if full output is needed>"
|
|
15941
16061
|
};
|
|
15942
16062
|
}
|
|
15943
16063
|
}
|
|
15944
16064
|
}
|
|
15945
16065
|
return messages;
|
|
15946
16066
|
};
|
|
15947
|
-
const
|
|
16067
|
+
const compactBashOutputs = (messages, protectedMessageCount = 10, compactionLevel = 1) => {
|
|
15948
16068
|
const protectedStart = getProtectedStartIndex(messages, protectedMessageCount);
|
|
16069
|
+
logger.info(`Compacting bash outputs at level ${compactionLevel}`);
|
|
15949
16070
|
const bashCommands = /* @__PURE__ */ new Map();
|
|
15950
16071
|
for (let i = 0; i < protectedStart; i++) {
|
|
15951
16072
|
const msg = messages[i];
|
|
@@ -16004,6 +16125,30 @@ const deduplicateBash = (messages, protectedMessageCount = 10) => {
|
|
|
16004
16125
|
if (!isPowerTool(serverName) || toolName !== POWER_TOOL_BASH) {
|
|
16005
16126
|
continue;
|
|
16006
16127
|
}
|
|
16128
|
+
if (compactionLevel >= 3) {
|
|
16129
|
+
part.output = {
|
|
16130
|
+
type: "text",
|
|
16131
|
+
value: "<result redacted due to compaction, run again if needed>"
|
|
16132
|
+
};
|
|
16133
|
+
continue;
|
|
16134
|
+
}
|
|
16135
|
+
if (part.output.type === "json" || part.output.type === "error-json") {
|
|
16136
|
+
const value = part.output.value;
|
|
16137
|
+
if (typeof value === "object" && value !== null) {
|
|
16138
|
+
const obj = value;
|
|
16139
|
+
const stdout = typeof obj.stdout === "string" ? obj.stdout : "";
|
|
16140
|
+
const stderr = typeof obj.stderr === "string" ? obj.stderr : "";
|
|
16141
|
+
const redactionMessage = "<output redacted due to compaction, run again if output is needed>";
|
|
16142
|
+
const redactionThreshold = compactionLevel >= 2 ? 0 : 30;
|
|
16143
|
+
if (stdout.length > redactionThreshold) {
|
|
16144
|
+
obj.stdout = redactionMessage;
|
|
16145
|
+
}
|
|
16146
|
+
if (stderr.length > redactionThreshold) {
|
|
16147
|
+
obj.stderr = redactionMessage;
|
|
16148
|
+
}
|
|
16149
|
+
}
|
|
16150
|
+
continue;
|
|
16151
|
+
}
|
|
16007
16152
|
if (part.output.type !== "text") {
|
|
16008
16153
|
continue;
|
|
16009
16154
|
}
|
|
@@ -16014,11 +16159,12 @@ const deduplicateBash = (messages, protectedMessageCount = 10) => {
|
|
|
16014
16159
|
const stderr = typeof parsed.stderr === "string" ? parsed.stderr : "";
|
|
16015
16160
|
const redactionMessage = "<output redacted due to compaction, run again if output is needed>";
|
|
16016
16161
|
let modified = false;
|
|
16017
|
-
|
|
16162
|
+
const redactionThreshold = compactionLevel >= 2 ? 0 : 30;
|
|
16163
|
+
if (stdout.length > redactionThreshold) {
|
|
16018
16164
|
parsed.stdout = redactionMessage;
|
|
16019
16165
|
modified = true;
|
|
16020
16166
|
}
|
|
16021
|
-
if (stderr.length >
|
|
16167
|
+
if (stderr.length > redactionThreshold) {
|
|
16022
16168
|
parsed.stderr = redactionMessage;
|
|
16023
16169
|
modified = true;
|
|
16024
16170
|
}
|
|
@@ -16148,6 +16294,8 @@ class Task {
|
|
|
16148
16294
|
tokensInfo;
|
|
16149
16295
|
queuedPrompts = [];
|
|
16150
16296
|
isCompacting = false;
|
|
16297
|
+
lastSmartCompactionMessageCount = 0;
|
|
16298
|
+
smartCompactionLevel = CompactionLevel.One;
|
|
16151
16299
|
taskDataPath;
|
|
16152
16300
|
contextManager;
|
|
16153
16301
|
agent;
|
|
@@ -16741,6 +16889,7 @@ class Task {
|
|
|
16741
16889
|
provider: this.task.provider || profile.provider,
|
|
16742
16890
|
model: this.task.model || profile.model
|
|
16743
16891
|
});
|
|
16892
|
+
this.smartCompactionLevel = 1;
|
|
16744
16893
|
const agentMessages = await this.agent.runAgent(
|
|
16745
16894
|
this,
|
|
16746
16895
|
profile,
|
|
@@ -18126,7 +18275,9 @@ ${contentText}</agent-response>`;
|
|
|
18126
18275
|
const removedMessages = this.contextManager.removeMessagesUpToUserMessage(messageId);
|
|
18127
18276
|
const originalUserMessage = removedMessages[0];
|
|
18128
18277
|
if (!originalUserMessage || originalUserMessage.role !== MessageRole.User) {
|
|
18129
|
-
logger.warn("Could not find the specified user message to redo.", {
|
|
18278
|
+
logger.warn("Could not find the specified user message to redo.", {
|
|
18279
|
+
messageId
|
|
18280
|
+
});
|
|
18130
18281
|
return;
|
|
18131
18282
|
}
|
|
18132
18283
|
const originalText = extractTextContent(originalUserMessage.content);
|
|
@@ -18243,7 +18394,24 @@ ${contentText}</agent-response>`;
|
|
|
18243
18394
|
return [];
|
|
18244
18395
|
}
|
|
18245
18396
|
await this.contextManager.backupContext();
|
|
18246
|
-
const
|
|
18397
|
+
const messagesSinceLastCompaction = contextMessages.length - this.lastSmartCompactionMessageCount;
|
|
18398
|
+
if (messagesSinceLastCompaction <= 3) {
|
|
18399
|
+
logger.info("Increasing compaction level to aggressive due to low message count since last compaction.", {
|
|
18400
|
+
messagesSinceLastCompaction,
|
|
18401
|
+
smartCompactionLevel: this.smartCompactionLevel
|
|
18402
|
+
});
|
|
18403
|
+
this.smartCompactionLevel = Math.min(this.smartCompactionLevel + 1, CompactionLevel.Three);
|
|
18404
|
+
} else if (messagesSinceLastCompaction > 5 && this.smartCompactionLevel > CompactionLevel.One) {
|
|
18405
|
+
logger.info("Decreasing compaction level to mild due to high message count since last compaction.", {
|
|
18406
|
+
messagesSinceLastCompaction
|
|
18407
|
+
});
|
|
18408
|
+
this.smartCompactionLevel = Math.max(this.smartCompactionLevel - 1, CompactionLevel.One);
|
|
18409
|
+
}
|
|
18410
|
+
logger.debug("Current compaction level:", {
|
|
18411
|
+
smartCompactionLevel: this.smartCompactionLevel
|
|
18412
|
+
});
|
|
18413
|
+
const compactedMessages = await smartCompactMessages(contextMessages, 10, this.smartCompactionLevel);
|
|
18414
|
+
this.lastSmartCompactionMessageCount = compactedMessages.length;
|
|
18247
18415
|
this.contextManager.setContextMessages(compactedMessages);
|
|
18248
18416
|
await this.contextManager.loadMessages(compactedMessages, false);
|
|
18249
18417
|
await this.updateContextInfo();
|
|
@@ -18257,7 +18425,7 @@ ${contentText}</agent-response>`;
|
|
|
18257
18425
|
if (!contextMessages) {
|
|
18258
18426
|
contextMessages = await this.contextManager.getContextMessages();
|
|
18259
18427
|
}
|
|
18260
|
-
const userMessage = contextMessages
|
|
18428
|
+
const userMessage = contextMessages.find((msg) => msg.role === MessageRole.User);
|
|
18261
18429
|
if (!userMessage) {
|
|
18262
18430
|
this.addLogMessage("warning", "No conversation to compact.");
|
|
18263
18431
|
return;
|
|
@@ -18937,46 +19105,96 @@ Only answer with the commit message, nothing else.`,
|
|
|
18937
19105
|
await this.sendUpdatedFilesUpdated();
|
|
18938
19106
|
await this.sendWorktreeIntegrationStatusUpdated();
|
|
18939
19107
|
}
|
|
18940
|
-
async
|
|
18941
|
-
if (!this.task.worktree) {
|
|
19108
|
+
async switchToLocalWorkingMode(options) {
|
|
19109
|
+
if (options?.mergeBeforeSwitch && !this.task.worktree) {
|
|
18942
19110
|
throw new Error("No worktree exists for this task");
|
|
18943
19111
|
}
|
|
18944
|
-
logger.info("
|
|
19112
|
+
logger.info("Switching to local working mode", {
|
|
18945
19113
|
baseDir: this.project.baseDir,
|
|
18946
|
-
taskId: this.taskId
|
|
19114
|
+
taskId: this.taskId,
|
|
19115
|
+
mergeBeforeSwitch: options?.mergeBeforeSwitch ?? false
|
|
18947
19116
|
});
|
|
18948
19117
|
await this.waitForCurrentPromptToFinish();
|
|
18949
|
-
|
|
18950
|
-
|
|
18951
|
-
|
|
18952
|
-
|
|
18953
|
-
|
|
18954
|
-
|
|
18955
|
-
this.
|
|
18956
|
-
|
|
18957
|
-
|
|
18958
|
-
|
|
18959
|
-
|
|
18960
|
-
|
|
18961
|
-
|
|
18962
|
-
|
|
18963
|
-
|
|
18964
|
-
|
|
18965
|
-
|
|
18966
|
-
|
|
18967
|
-
|
|
18968
|
-
|
|
18969
|
-
|
|
18970
|
-
|
|
18971
|
-
|
|
18972
|
-
|
|
18973
|
-
|
|
18974
|
-
|
|
18975
|
-
|
|
18976
|
-
|
|
18977
|
-
|
|
18978
|
-
|
|
19118
|
+
if (options?.mergeBeforeSwitch && this.task.worktree) {
|
|
19119
|
+
try {
|
|
19120
|
+
const effectiveTargetBranch = options.targetBranch || await this.worktreeManager.getProjectMainBranch(this.project.baseDir);
|
|
19121
|
+
this.addLogMessage("loading", `Merging worktree to ${effectiveTargetBranch} branch and switching to local mode...`);
|
|
19122
|
+
const settings = this.store.getSettings();
|
|
19123
|
+
const symlinkFolders = settings.taskSettings.worktreeSymlinkFolders || [];
|
|
19124
|
+
const mergeState = await this.worktreeManager.mergeWorktreeToMainWithUncommitted(
|
|
19125
|
+
this.project.baseDir,
|
|
19126
|
+
this.task.id,
|
|
19127
|
+
this.task.worktree.path,
|
|
19128
|
+
false,
|
|
19129
|
+
this.task.name || `Task ${this.taskId} changes`,
|
|
19130
|
+
options.targetBranch,
|
|
19131
|
+
symlinkFolders
|
|
19132
|
+
);
|
|
19133
|
+
await this.saveTask({ lastMergeState: mergeState });
|
|
19134
|
+
this.addLogMessage("info", `Successfully merged worktree to ${effectiveTargetBranch} branch`, true);
|
|
19135
|
+
} catch (error) {
|
|
19136
|
+
logger.error("Failed to merge worktree and switch to local:", { error });
|
|
19137
|
+
const isConflict = error instanceof GitError && (error.gitOutput?.toLowerCase().includes("resolve all conflicts") || error.message?.toLowerCase().includes("conflicts must be resolved first") || error.gitOutput?.toLowerCase().includes("conflicts must be resolved first"));
|
|
19138
|
+
this.addLogMessage(
|
|
19139
|
+
"error",
|
|
19140
|
+
isConflict ? "worktree.mergeConflicts" : error instanceof GitError ? error.getErrorDetails() : `Failed to merge worktree: ${error instanceof Error ? error.message : String(error)}`,
|
|
19141
|
+
true,
|
|
19142
|
+
void 0,
|
|
19143
|
+
isConflict ? ["rebase-worktree"] : void 0
|
|
19144
|
+
);
|
|
19145
|
+
await this.sendUpdatedFilesUpdated();
|
|
19146
|
+
await this.sendWorktreeIntegrationStatusUpdated();
|
|
19147
|
+
throw error;
|
|
19148
|
+
}
|
|
18979
19149
|
}
|
|
19150
|
+
await this.updateTask({ workingMode: "local" });
|
|
19151
|
+
}
|
|
19152
|
+
async switchToWorktreeWorkingMode(options) {
|
|
19153
|
+
logger.info("Switching to worktree working mode", {
|
|
19154
|
+
baseDir: this.project.baseDir,
|
|
19155
|
+
taskId: this.taskId,
|
|
19156
|
+
carryOverUncommittedChanges: options?.carryOverUncommittedChanges ?? false,
|
|
19157
|
+
dropSourceChanges: options?.dropSourceChanges ?? true
|
|
19158
|
+
});
|
|
19159
|
+
await this.waitForCurrentPromptToFinish();
|
|
19160
|
+
let stashId = null;
|
|
19161
|
+
const settings = this.store.getSettings();
|
|
19162
|
+
const symlinkFolders = settings.taskSettings.worktreeSymlinkFolders || [];
|
|
19163
|
+
if (options?.carryOverUncommittedChanges) {
|
|
19164
|
+
const timestamp = Date.now();
|
|
19165
|
+
const shortId = this.taskId.length > 24 ? this.taskId.substring(24) : this.taskId;
|
|
19166
|
+
stashId = `local-${shortId}-to-worktree-${timestamp}`;
|
|
19167
|
+
try {
|
|
19168
|
+
const stashResult = await this.worktreeManager.stashUncommittedChanges(
|
|
19169
|
+
stashId,
|
|
19170
|
+
this.project.baseDir,
|
|
19171
|
+
"Uncommitted changes to carry over to worktree",
|
|
19172
|
+
symlinkFolders
|
|
19173
|
+
);
|
|
19174
|
+
if (!stashResult) {
|
|
19175
|
+
stashId = null;
|
|
19176
|
+
}
|
|
19177
|
+
} catch (error) {
|
|
19178
|
+
logger.error("Failed to stash uncommitted changes before worktree switch:", { error });
|
|
19179
|
+
stashId = null;
|
|
19180
|
+
}
|
|
19181
|
+
}
|
|
19182
|
+
await this.updateTask({ workingMode: "worktree" });
|
|
19183
|
+
if (stashId && this.task.worktree) {
|
|
19184
|
+
try {
|
|
19185
|
+
await this.worktreeManager.applyStash(this.task.worktree.path, stashId);
|
|
19186
|
+
if (!options?.dropSourceChanges) {
|
|
19187
|
+
await this.worktreeManager.applyStash(this.project.baseDir, stashId);
|
|
19188
|
+
}
|
|
19189
|
+
await this.worktreeManager.dropStash(this.project.baseDir, stashId);
|
|
19190
|
+
} catch (error) {
|
|
19191
|
+
logger.error("Failed to apply stashed changes to worktree:", { error });
|
|
19192
|
+
}
|
|
19193
|
+
}
|
|
19194
|
+
void this.sendUpdatedFilesUpdated();
|
|
19195
|
+
}
|
|
19196
|
+
async getLocalUncommittedFiles() {
|
|
19197
|
+
return await this.worktreeManager.getUncommittedFiles(this.project.baseDir);
|
|
18980
19198
|
}
|
|
18981
19199
|
async applyUncommittedChanges(targetBranch) {
|
|
18982
19200
|
if (!this.task.worktree) {
|
|
@@ -19166,7 +19384,13 @@ ${diff}
|
|
|
19166
19384
|
if (success) {
|
|
19167
19385
|
const newHead = await this.worktreeManager.getHeadCommit(this.task.worktree.path);
|
|
19168
19386
|
if (newHead) {
|
|
19169
|
-
await this.saveTask({
|
|
19387
|
+
await this.saveTask({
|
|
19388
|
+
worktree: {
|
|
19389
|
+
...this.task.worktree,
|
|
19390
|
+
baseCommit: newHead,
|
|
19391
|
+
baseBranch: effectiveFromBranch
|
|
19392
|
+
}
|
|
19393
|
+
});
|
|
19170
19394
|
}
|
|
19171
19395
|
this.addLogMessage("info", "Worktree rebased successfully", true);
|
|
19172
19396
|
return;
|
|
@@ -20782,132 +21006,6 @@ const anthropicCompatibleProviderStrategy = {
|
|
|
20782
21006
|
// Cache control
|
|
20783
21007
|
getCacheControl: getAnthropicCacheControl
|
|
20784
21008
|
};
|
|
20785
|
-
const loadAuggieSdk = async () => import("@augmentcode/auggie-sdk");
|
|
20786
|
-
const AUGGIE_MODELS = [
|
|
20787
|
-
{
|
|
20788
|
-
id: "claude-haiku-4-5",
|
|
20789
|
-
maxInputTokens: 2e5,
|
|
20790
|
-
maxOutputTokensLimit: 8192
|
|
20791
|
-
},
|
|
20792
|
-
{
|
|
20793
|
-
id: "claude-sonnet-4",
|
|
20794
|
-
maxInputTokens: 2e5,
|
|
20795
|
-
maxOutputTokensLimit: 16384
|
|
20796
|
-
},
|
|
20797
|
-
{
|
|
20798
|
-
id: "claude-sonnet-4-5",
|
|
20799
|
-
maxInputTokens: 2e5,
|
|
20800
|
-
maxOutputTokensLimit: 16384
|
|
20801
|
-
},
|
|
20802
|
-
{
|
|
20803
|
-
id: "claude-opus-4-5",
|
|
20804
|
-
maxInputTokens: 2e5,
|
|
20805
|
-
maxOutputTokensLimit: 32768
|
|
20806
|
-
},
|
|
20807
|
-
{
|
|
20808
|
-
id: "claude-opus-4-6",
|
|
20809
|
-
maxInputTokens: 2e5,
|
|
20810
|
-
maxOutputTokensLimit: 32768
|
|
20811
|
-
},
|
|
20812
|
-
{
|
|
20813
|
-
id: "claude-opus-4-7",
|
|
20814
|
-
maxInputTokens: 2e5,
|
|
20815
|
-
maxOutputTokensLimit: 32768
|
|
20816
|
-
},
|
|
20817
|
-
{ id: "gpt-5-1", maxInputTokens: 2e5, maxOutputTokensLimit: 16384 },
|
|
20818
|
-
{ id: "gpt-5-2", maxInputTokens: 2e5, maxOutputTokensLimit: 16384 },
|
|
20819
|
-
{ id: "gpt-5-4", maxInputTokens: 2e5, maxOutputTokensLimit: 16384 }
|
|
20820
|
-
];
|
|
20821
|
-
const loadAuggieModels = async (profile, _settings) => {
|
|
20822
|
-
if (!isAuggieProvider(profile.provider)) {
|
|
20823
|
-
return {
|
|
20824
|
-
models: [],
|
|
20825
|
-
success: false
|
|
20826
|
-
};
|
|
20827
|
-
}
|
|
20828
|
-
const models = AUGGIE_MODELS.map((model) => ({
|
|
20829
|
-
id: model.id,
|
|
20830
|
-
providerId: profile.id,
|
|
20831
|
-
maxInputTokens: model.maxInputTokens,
|
|
20832
|
-
maxOutputTokensLimit: model.maxOutputTokensLimit
|
|
20833
|
-
}));
|
|
20834
|
-
logger.info(`Loaded ${models.length} Auggie models for profile ${profile.id}`);
|
|
20835
|
-
return { models, success: true };
|
|
20836
|
-
};
|
|
20837
|
-
const hasAuggieEnvVars = (settings) => {
|
|
20838
|
-
if (getEffectiveEnvironmentVariable("AUGMENT_API_TOKEN", settings, void 0)?.value && getEffectiveEnvironmentVariable("AUGMENT_API_URL", settings, void 0)?.value) {
|
|
20839
|
-
return true;
|
|
20840
|
-
}
|
|
20841
|
-
const auggieSessionFile = path.join(os.homedir(), ".augment", "session.json");
|
|
20842
|
-
if (findExecutableInPath("auggie") && fs$1.existsSync(auggieSessionFile)) {
|
|
20843
|
-
return true;
|
|
20844
|
-
}
|
|
20845
|
-
return false;
|
|
20846
|
-
};
|
|
20847
|
-
const getAuggieAiderMapping = (provider, modelId) => {
|
|
20848
|
-
const auggieProvider = provider.provider;
|
|
20849
|
-
const envVars = {};
|
|
20850
|
-
if (auggieProvider.apiKey) {
|
|
20851
|
-
envVars.AUGMENT_API_TOKEN = auggieProvider.apiKey;
|
|
20852
|
-
}
|
|
20853
|
-
if (auggieProvider.apiUrl) {
|
|
20854
|
-
envVars.AUGMENT_API_URL = auggieProvider.apiUrl;
|
|
20855
|
-
}
|
|
20856
|
-
return {
|
|
20857
|
-
modelName: `auggie/${modelId}`,
|
|
20858
|
-
environmentVariables: envVars
|
|
20859
|
-
};
|
|
20860
|
-
};
|
|
20861
|
-
const createAuggieLlm = async (profile, model, settings, projectDir) => {
|
|
20862
|
-
const provider = profile.provider;
|
|
20863
|
-
let apiKey = provider.apiKey;
|
|
20864
|
-
let apiUrl = provider.apiUrl;
|
|
20865
|
-
if (!apiKey) {
|
|
20866
|
-
const effectiveVar = getEffectiveEnvironmentVariable("AUGMENT_API_TOKEN", settings, projectDir);
|
|
20867
|
-
if (effectiveVar) {
|
|
20868
|
-
apiKey = effectiveVar.value;
|
|
20869
|
-
logger.debug(`Loaded AUGMENT_API_TOKEN from ${effectiveVar.source}`);
|
|
20870
|
-
}
|
|
20871
|
-
}
|
|
20872
|
-
if (!apiUrl) {
|
|
20873
|
-
const effectiveUrlVar = getEffectiveEnvironmentVariable("AUGMENT_API_URL", settings, projectDir);
|
|
20874
|
-
if (effectiveUrlVar) {
|
|
20875
|
-
apiUrl = effectiveUrlVar.value;
|
|
20876
|
-
logger.debug(`Loaded AUGMENT_API_URL from ${effectiveUrlVar.source}`);
|
|
20877
|
-
}
|
|
20878
|
-
}
|
|
20879
|
-
if (apiKey && !apiUrl) {
|
|
20880
|
-
throw new Error("API URL is required when API key is provided.");
|
|
20881
|
-
}
|
|
20882
|
-
const { AugmentLanguageModel, resolveAugmentCredentials } = await loadAuggieSdk();
|
|
20883
|
-
const AugmentLanguageModelCtor = AugmentLanguageModel;
|
|
20884
|
-
if (apiKey && apiUrl) {
|
|
20885
|
-
return new AugmentLanguageModelCtor(model.id, {
|
|
20886
|
-
apiKey,
|
|
20887
|
-
apiUrl
|
|
20888
|
-
});
|
|
20889
|
-
} else {
|
|
20890
|
-
const credentials = await resolveAugmentCredentials();
|
|
20891
|
-
return new AugmentLanguageModelCtor(model.id, credentials);
|
|
20892
|
-
}
|
|
20893
|
-
};
|
|
20894
|
-
const getAuggieUsageReport = (_task, _provider, model) => {
|
|
20895
|
-
return {
|
|
20896
|
-
model: model.id,
|
|
20897
|
-
sentTokens: 0,
|
|
20898
|
-
receivedTokens: 0,
|
|
20899
|
-
messageCost: 0,
|
|
20900
|
-
agentTotalCost: 0
|
|
20901
|
-
};
|
|
20902
|
-
};
|
|
20903
|
-
const auggieProviderStrategy = {
|
|
20904
|
-
createLlm: createAuggieLlm,
|
|
20905
|
-
getUsageReport: getAuggieUsageReport,
|
|
20906
|
-
loadModels: loadAuggieModels,
|
|
20907
|
-
hasEnvVars: hasAuggieEnvVars,
|
|
20908
|
-
getAiderMapping: getAuggieAiderMapping,
|
|
20909
|
-
getModelInfo: getDefaultModelInfo
|
|
20910
|
-
};
|
|
20911
21009
|
const extractResourceNameFromEndpoint = (endpoint) => {
|
|
20912
21010
|
try {
|
|
20913
21011
|
const url = new URL(endpoint);
|
|
@@ -21333,199 +21431,6 @@ const cerebrasProviderStrategy = {
|
|
|
21333
21431
|
getAiderMapping: getCerebrasAiderMapping,
|
|
21334
21432
|
getModelInfo: getDefaultModelInfo
|
|
21335
21433
|
};
|
|
21336
|
-
const loadClaudeAgentSdkModels = async (profile, _settings) => {
|
|
21337
|
-
if (!isClaudeAgentSdkProvider(profile.provider)) {
|
|
21338
|
-
return {
|
|
21339
|
-
models: [],
|
|
21340
|
-
success: false
|
|
21341
|
-
};
|
|
21342
|
-
}
|
|
21343
|
-
try {
|
|
21344
|
-
const models = [
|
|
21345
|
-
{
|
|
21346
|
-
id: "haiku",
|
|
21347
|
-
providerId: profile.id,
|
|
21348
|
-
maxInputTokens: 2e5,
|
|
21349
|
-
maxOutputTokensLimit: 64e3
|
|
21350
|
-
},
|
|
21351
|
-
{
|
|
21352
|
-
id: "sonnet",
|
|
21353
|
-
providerId: profile.id,
|
|
21354
|
-
maxInputTokens: 2e5,
|
|
21355
|
-
maxOutputTokens: 64e3
|
|
21356
|
-
},
|
|
21357
|
-
{
|
|
21358
|
-
id: "opus",
|
|
21359
|
-
providerId: profile.id,
|
|
21360
|
-
maxInputTokens: 2e5,
|
|
21361
|
-
maxOutputTokensLimit: 64e3
|
|
21362
|
-
}
|
|
21363
|
-
];
|
|
21364
|
-
logger.info(`Loaded ${models.length} Claude Agent SDK models for profile ${profile.id}`);
|
|
21365
|
-
return { models, success: true };
|
|
21366
|
-
} catch (error) {
|
|
21367
|
-
const errorMsg = typeof error === "string" ? error : error instanceof Error ? error.message : "Unknown error loading Claude Agent SDK models";
|
|
21368
|
-
logger.error("Error loading Claude Agent SDK models:", error);
|
|
21369
|
-
return { models: [], success: false, error: errorMsg };
|
|
21370
|
-
}
|
|
21371
|
-
};
|
|
21372
|
-
const hasClaudeAgentSdkEnvVars = () => {
|
|
21373
|
-
return findExecutableInPath("claude") !== null;
|
|
21374
|
-
};
|
|
21375
|
-
const getClaudeAgentSdkAiderMapping = (_provider, modelId) => {
|
|
21376
|
-
return {
|
|
21377
|
-
environmentVariables: {},
|
|
21378
|
-
modelName: `claude-agent-sdk/${modelId}`
|
|
21379
|
-
};
|
|
21380
|
-
};
|
|
21381
|
-
const normalizeAiSdkToolSet = (toolSet) => {
|
|
21382
|
-
const normalizedToolSet = {};
|
|
21383
|
-
for (const [toolName, toolDefinition] of Object.entries(toolSet)) {
|
|
21384
|
-
let normalizedTool = { ...toolDefinition };
|
|
21385
|
-
const inputSchema = toolDefinition.inputSchema;
|
|
21386
|
-
if (inputSchema && typeof inputSchema === "object" && "jsonSchema" in inputSchema) {
|
|
21387
|
-
const jsonSchemaObj = inputSchema.jsonSchema;
|
|
21388
|
-
const schema = typeof jsonSchemaObj === "function" ? jsonSchemaObj() : jsonSchemaObj;
|
|
21389
|
-
const zodShape = jsonSchemaToZod.JSONSchemaToZod.convert(schema);
|
|
21390
|
-
normalizedTool = {
|
|
21391
|
-
...toolDefinition,
|
|
21392
|
-
inputSchema: zodShape
|
|
21393
|
-
};
|
|
21394
|
-
logger.debug(`Converted JSONSchema to Zod for tool: ${toolName}`);
|
|
21395
|
-
}
|
|
21396
|
-
if (toolName === `${AIDER_TOOL_GROUP_NAME}${TOOL_GROUP_NAME_SEPARATOR}${AIDER_TOOL_RUN_PROMPT}`) {
|
|
21397
|
-
const originalExecute = normalizedTool.execute;
|
|
21398
|
-
if (!originalExecute) {
|
|
21399
|
-
normalizedToolSet[toolName] = normalizedTool;
|
|
21400
|
-
continue;
|
|
21401
|
-
}
|
|
21402
|
-
normalizedToolSet[toolName] = {
|
|
21403
|
-
...normalizedTool,
|
|
21404
|
-
execute: async (args, options) => {
|
|
21405
|
-
const result = await originalExecute(args, options);
|
|
21406
|
-
if (result && typeof result === "object") {
|
|
21407
|
-
delete result.responses;
|
|
21408
|
-
}
|
|
21409
|
-
return result;
|
|
21410
|
-
}
|
|
21411
|
-
};
|
|
21412
|
-
} else if (toolName === `${SUBAGENTS_TOOL_GROUP_NAME}${TOOL_GROUP_NAME_SEPARATOR}${SUBAGENTS_TOOL_RUN_TASK}`) {
|
|
21413
|
-
const originalExecute = normalizedTool.execute;
|
|
21414
|
-
if (!originalExecute) {
|
|
21415
|
-
normalizedToolSet[toolName] = normalizedTool;
|
|
21416
|
-
continue;
|
|
21417
|
-
}
|
|
21418
|
-
normalizedToolSet[toolName] = {
|
|
21419
|
-
...normalizedTool,
|
|
21420
|
-
execute: async (args, options) => {
|
|
21421
|
-
const result = await originalExecute(args, options);
|
|
21422
|
-
if (result && typeof result === "object") {
|
|
21423
|
-
try {
|
|
21424
|
-
const messages = result.messages;
|
|
21425
|
-
if (Array.isArray(messages) && messages.length > 0) {
|
|
21426
|
-
const lastMessage = messages[messages.length - 1];
|
|
21427
|
-
return {
|
|
21428
|
-
messages: [lastMessage],
|
|
21429
|
-
promptContext: result.promptContext
|
|
21430
|
-
};
|
|
21431
|
-
}
|
|
21432
|
-
} catch (error) {
|
|
21433
|
-
logger.warn("Failed to optimize subagent result:", error);
|
|
21434
|
-
}
|
|
21435
|
-
}
|
|
21436
|
-
return result;
|
|
21437
|
-
}
|
|
21438
|
-
};
|
|
21439
|
-
} else {
|
|
21440
|
-
normalizedToolSet[toolName] = normalizedTool;
|
|
21441
|
-
}
|
|
21442
|
-
}
|
|
21443
|
-
return normalizedToolSet;
|
|
21444
|
-
};
|
|
21445
|
-
const createClaudeAgentSdkLlm = (_profile, model, _settings, _projectDir, toolSet, systemPrompt, providerMetadata) => {
|
|
21446
|
-
const settings = {
|
|
21447
|
-
env: {
|
|
21448
|
-
// setting MAX_MCP_OUTPUT_TOKENS to a high number to avoid errors
|
|
21449
|
-
MAX_MCP_OUTPUT_TOKENS: "9999999"
|
|
21450
|
-
},
|
|
21451
|
-
// for now only tools from AiderDesk are allowed
|
|
21452
|
-
disallowedTools: [
|
|
21453
|
-
"AskUserQuestion",
|
|
21454
|
-
"Bash",
|
|
21455
|
-
"TaskOutput",
|
|
21456
|
-
"Edit",
|
|
21457
|
-
"EnterPlanMode",
|
|
21458
|
-
"ExitPlanMode",
|
|
21459
|
-
"Glob",
|
|
21460
|
-
"Grep",
|
|
21461
|
-
"KillShell",
|
|
21462
|
-
"MCPSearch",
|
|
21463
|
-
"NotebookEdit",
|
|
21464
|
-
"Read",
|
|
21465
|
-
"Skill",
|
|
21466
|
-
"Task",
|
|
21467
|
-
"TaskCreate",
|
|
21468
|
-
"TaskGet",
|
|
21469
|
-
"TaskList",
|
|
21470
|
-
"TaskUpdate",
|
|
21471
|
-
"TodoWrite",
|
|
21472
|
-
"WebFetch",
|
|
21473
|
-
"WebSearch",
|
|
21474
|
-
"Write",
|
|
21475
|
-
"LSP"
|
|
21476
|
-
]
|
|
21477
|
-
};
|
|
21478
|
-
if (providerMetadata && typeof providerMetadata === "object" && "claude-code" in providerMetadata) {
|
|
21479
|
-
const metadata = providerMetadata["claude-code"] || {};
|
|
21480
|
-
settings.resume = metadata.sessionId;
|
|
21481
|
-
}
|
|
21482
|
-
if (!isDev() && isElectron()) {
|
|
21483
|
-
settings.pathToClaudeCodeExecutable = CLAUDE_CODE_EXECUTABLE_PATH;
|
|
21484
|
-
}
|
|
21485
|
-
if (toolSet) {
|
|
21486
|
-
logger.debug(`Adding ${Object.keys(toolSet).length} tools to Claude Agent SDK`, {
|
|
21487
|
-
tools: Object.keys(toolSet)
|
|
21488
|
-
});
|
|
21489
|
-
settings.aiSdkTools = normalizeAiSdkToolSet(toolSet);
|
|
21490
|
-
settings.allowedTools = ["mcp__ai-sdk"];
|
|
21491
|
-
} else {
|
|
21492
|
-
settings.allowedTools = [];
|
|
21493
|
-
}
|
|
21494
|
-
if (systemPrompt) {
|
|
21495
|
-
settings.systemPrompt = systemPrompt;
|
|
21496
|
-
}
|
|
21497
|
-
return aiSdkProviderClaudeCode.claudeCode(model.id, settings);
|
|
21498
|
-
};
|
|
21499
|
-
const getClaudeAgentSdkUsageReport = (task, provider, model, _usage, providerMetadata) => {
|
|
21500
|
-
const data = providerMetadata["claude-code"] || {};
|
|
21501
|
-
const usage = data.lastMessageRawUsage || data.rawUsage || {};
|
|
21502
|
-
logger.debug("Claude Agent SDK usage:", { usage: _usage, providerMetadata });
|
|
21503
|
-
const sentTokens = usage.input_tokens || 0;
|
|
21504
|
-
const receivedTokens = usage.output_tokens || 0;
|
|
21505
|
-
const cacheWriteTokens = usage.cache_creation_input_tokens || 0;
|
|
21506
|
-
const cacheReadTokens = usage.cache_read_input_tokens || 0;
|
|
21507
|
-
const messageCost = calculateCost(model, sentTokens, receivedTokens, cacheReadTokens);
|
|
21508
|
-
return {
|
|
21509
|
-
model: `${provider.id}/${model.id}`,
|
|
21510
|
-
sentTokens: sentTokens + cacheReadTokens,
|
|
21511
|
-
receivedTokens: receivedTokens + cacheWriteTokens,
|
|
21512
|
-
messageCost,
|
|
21513
|
-
agentTotalCost: task.task.agentTotalCost + messageCost
|
|
21514
|
-
};
|
|
21515
|
-
};
|
|
21516
|
-
const getClaudeAgentSdkProviderParameters = () => {
|
|
21517
|
-
return {
|
|
21518
|
-
system: void 0
|
|
21519
|
-
};
|
|
21520
|
-
};
|
|
21521
|
-
const claudeAgentSdkProviderStrategy = {
|
|
21522
|
-
createLlm: createClaudeAgentSdkLlm,
|
|
21523
|
-
getUsageReport: getClaudeAgentSdkUsageReport,
|
|
21524
|
-
loadModels: loadClaudeAgentSdkModels,
|
|
21525
|
-
hasEnvVars: hasClaudeAgentSdkEnvVars,
|
|
21526
|
-
getAiderMapping: getClaudeAgentSdkAiderMapping,
|
|
21527
|
-
getProviderParameters: getClaudeAgentSdkProviderParameters
|
|
21528
|
-
};
|
|
21529
21434
|
const loadDeepseekModels = async (profile, settings) => {
|
|
21530
21435
|
if (!isDeepseekProvider(profile.provider)) {
|
|
21531
21436
|
return { models: [], success: false };
|
|
@@ -22584,6 +22489,20 @@ const loadMinimaxModels = async (profile) => {
|
|
|
22584
22489
|
};
|
|
22585
22490
|
}
|
|
22586
22491
|
const hardcodedModels = [
|
|
22492
|
+
{
|
|
22493
|
+
id: "MiniMax-M3",
|
|
22494
|
+
providerId: profile.id,
|
|
22495
|
+
maxInputTokens: 1e6,
|
|
22496
|
+
maxOutputTokensLimit: 131072,
|
|
22497
|
+
inputCostPerToken: 3e-7,
|
|
22498
|
+
// 0.3 per 1M tokens
|
|
22499
|
+
outputCostPerToken: 12e-7,
|
|
22500
|
+
// 1.2 per 1M tokens
|
|
22501
|
+
cacheReadInputTokenCost: 6e-8,
|
|
22502
|
+
// 0.06 per 1M tokens
|
|
22503
|
+
cacheWriteInputTokenCost: 375e-9
|
|
22504
|
+
// 0.375 per 1M tokens
|
|
22505
|
+
},
|
|
22587
22506
|
{
|
|
22588
22507
|
id: "MiniMax-M2.7",
|
|
22589
22508
|
providerId: profile.id,
|
|
@@ -22883,7 +22802,7 @@ const loadNeuralwattModels = async (profile, settings) => {
|
|
|
22883
22802
|
return { models: [], success: false, error: errorMsg };
|
|
22884
22803
|
}
|
|
22885
22804
|
const data = await response.json();
|
|
22886
|
-
logger.
|
|
22805
|
+
logger.debug(`Received response from Neuralwatt models API for profile ${profile.id}`, { data });
|
|
22887
22806
|
const models = data.data?.map((model) => {
|
|
22888
22807
|
const metadata = model.metadata;
|
|
22889
22808
|
const pricing = metadata?.pricing;
|
|
@@ -24302,7 +24221,7 @@ const zaiPlanProviderStrategy = {
|
|
|
24302
24221
|
const MODELS_META_URL = "https://models.dev/api.json";
|
|
24303
24222
|
const MODELS_FILE = path.join(AIDER_DESK_DATA_DIR, "models.json");
|
|
24304
24223
|
const PROVIDER_MODELS_CACHE_FILE = path.join(AIDER_DESK_CACHE_DIR, "provider-models.json");
|
|
24305
|
-
const PROVIDER_MODELS_CACHE_VERSION =
|
|
24224
|
+
const PROVIDER_MODELS_CACHE_VERSION = 2;
|
|
24306
24225
|
class ModelManager {
|
|
24307
24226
|
constructor(store, eventManager) {
|
|
24308
24227
|
this.store = store;
|
|
@@ -24318,11 +24237,9 @@ class ModelManager {
|
|
|
24318
24237
|
providerRegistry = {
|
|
24319
24238
|
anthropic: anthropicProviderStrategy,
|
|
24320
24239
|
"anthropic-compatible": anthropicCompatibleProviderStrategy,
|
|
24321
|
-
auggie: auggieProviderStrategy,
|
|
24322
24240
|
azure: azureProviderStrategy,
|
|
24323
24241
|
bedrock: bedrockProviderStrategy,
|
|
24324
24242
|
cerebras: cerebrasProviderStrategy,
|
|
24325
|
-
"claude-agent-sdk": claudeAgentSdkProviderStrategy,
|
|
24326
24243
|
deepseek: deepseekProviderStrategy,
|
|
24327
24244
|
gemini: geminiProviderStrategy,
|
|
24328
24245
|
"gemini-cli": geminiCliProviderStrategy,
|
|
@@ -24995,7 +24912,7 @@ class ModelManager {
|
|
|
24995
24912
|
const { provider } = registered;
|
|
24996
24913
|
this.providerRegistry[provider.provider.name] = {
|
|
24997
24914
|
...provider.strategy,
|
|
24998
|
-
createLlm: (profile2, model, settings, projectDir) => provider.strategy.createLlm(profile2, model, settings, projectDir),
|
|
24915
|
+
createLlm: (profile2, model, settings, projectDir, toolSet, systemPrompt, providerMetadata) => provider.strategy.createLlm(profile2, model, settings, projectDir, toolSet, systemPrompt, providerMetadata),
|
|
24999
24916
|
getUsageReport: provider.strategy.getUsageReport || getDefaultUsageReport,
|
|
25000
24917
|
getProviderOptions: provider.strategy.getProviderOptions ? (_provider, model) => provider.strategy.getProviderOptions(model) : void 0,
|
|
25001
24918
|
getProviderTools: provider.strategy.getProviderTools ? (_provider, model) => provider.strategy.getProviderTools(model) : void 0,
|
|
@@ -25053,7 +24970,11 @@ class ModelManager {
|
|
|
25053
24970
|
this.eventManager.sendProvidersUpdated(this.getProviders());
|
|
25054
24971
|
}
|
|
25055
24972
|
getProviders() {
|
|
25056
|
-
|
|
24973
|
+
const providersById = new Map(this.store.getProviders().map((p) => [p.id, p]));
|
|
24974
|
+
for (const extensionProfile of this.getExtensionProviderProfiles()) {
|
|
24975
|
+
providersById.set(extensionProfile.id, extensionProfile);
|
|
24976
|
+
}
|
|
24977
|
+
return [...providersById.values()];
|
|
25057
24978
|
}
|
|
25058
24979
|
getExtensionProviderProfiles() {
|
|
25059
24980
|
return [...this.extensionProviders.values()].map((e) => e.profile);
|
|
@@ -26620,7 +26541,7 @@ class ExtensionContextImpl {
|
|
|
26620
26541
|
return truncateToolResult(content, maxLines, maxSizeKB, maxTokens, saveToFile, truncationSuffix);
|
|
26621
26542
|
}
|
|
26622
26543
|
}
|
|
26623
|
-
const CACHE_TTL_MS = 24 * 60 * 60 * 1e3;
|
|
26544
|
+
const CACHE_TTL_MS$1 = 24 * 60 * 60 * 1e3;
|
|
26624
26545
|
class ExtensionFetcher {
|
|
26625
26546
|
cache = /* @__PURE__ */ new Map();
|
|
26626
26547
|
getAvailableExtensionsPromise = null;
|
|
@@ -26651,7 +26572,7 @@ class ExtensionFetcher {
|
|
|
26651
26572
|
async fetchExtensionsFromRepo(repoUrl, forceRefresh) {
|
|
26652
26573
|
const cached = this.cache.get(repoUrl);
|
|
26653
26574
|
const now = Date.now();
|
|
26654
|
-
if (!forceRefresh && cached && now - cached.timestamp < CACHE_TTL_MS) {
|
|
26575
|
+
if (!forceRefresh && cached && now - cached.timestamp < CACHE_TTL_MS$1) {
|
|
26655
26576
|
logger.debug(`[ExtensionFetcher] Using cached extensions for ${repoUrl}`);
|
|
26656
26577
|
return cached.extensions;
|
|
26657
26578
|
}
|
|
@@ -26963,6 +26884,67 @@ class ExtensionFetcher {
|
|
|
26963
26884
|
return this.convertToGitHubRawUrl(webUrl);
|
|
26964
26885
|
}
|
|
26965
26886
|
}
|
|
26887
|
+
const ESM_SH_BASE_URL = "https://esm.sh";
|
|
26888
|
+
const CACHE_TTL_MS = 24 * 60 * 60 * 1e3;
|
|
26889
|
+
const sanitizeLibraryName = (name) => {
|
|
26890
|
+
return name.replace(/[^a-zA-Z0-9_-]/g, "_");
|
|
26891
|
+
};
|
|
26892
|
+
class ExtensionLibraryLoader {
|
|
26893
|
+
cacheDir;
|
|
26894
|
+
constructor() {
|
|
26895
|
+
this.cacheDir = path.join(AIDER_DESK_CACHE_DIR, "extension-libraries");
|
|
26896
|
+
}
|
|
26897
|
+
getCachePath(librarySpec) {
|
|
26898
|
+
const sanitized = sanitizeLibraryName(librarySpec);
|
|
26899
|
+
return path.join(this.cacheDir, `${sanitized}.js`);
|
|
26900
|
+
}
|
|
26901
|
+
getMetaPath(librarySpec) {
|
|
26902
|
+
const sanitized = sanitizeLibraryName(librarySpec);
|
|
26903
|
+
return path.join(this.cacheDir, `${sanitized}.meta.json`);
|
|
26904
|
+
}
|
|
26905
|
+
async loadLibrary(librarySpec) {
|
|
26906
|
+
const cachePath = this.getCachePath(librarySpec);
|
|
26907
|
+
const metaPath = this.getMetaPath(librarySpec);
|
|
26908
|
+
try {
|
|
26909
|
+
await fs.access(cachePath);
|
|
26910
|
+
await fs.access(metaPath);
|
|
26911
|
+
try {
|
|
26912
|
+
const meta = JSON.parse(await fs.readFile(metaPath, "utf-8"));
|
|
26913
|
+
const age = Date.now() - new Date(meta.fetchedAt).getTime();
|
|
26914
|
+
if (age < CACHE_TTL_MS) {
|
|
26915
|
+
logger.debug(`[ExtensionLibraryLoader] Cache hit for ${librarySpec}`);
|
|
26916
|
+
return await fs.readFile(cachePath, "utf-8");
|
|
26917
|
+
}
|
|
26918
|
+
logger.info(`[ExtensionLibraryLoader] Cache stale for ${librarySpec} (age: ${Math.round(age / 1e3 / 60)}min), re-fetching`);
|
|
26919
|
+
} catch {
|
|
26920
|
+
logger.warn(`[ExtensionLibraryLoader] Failed to read meta for ${librarySpec}, re-fetching`);
|
|
26921
|
+
}
|
|
26922
|
+
} catch {
|
|
26923
|
+
}
|
|
26924
|
+
logger.info(`[ExtensionLibraryLoader] Fetching ${librarySpec} from esm.sh`);
|
|
26925
|
+
const url = `${ESM_SH_BASE_URL}/${librarySpec}?external=react,react-dom,react/jsx-runtime,react/jsx-dev-runtime&bundle-deps&bundle`;
|
|
26926
|
+
let response = await fetchWithTimeout(url);
|
|
26927
|
+
if (!response.ok) {
|
|
26928
|
+
throw new Error(`Failed to fetch library ${librarySpec} from esm.sh: ${response.status} ${response.statusText}`);
|
|
26929
|
+
}
|
|
26930
|
+
let source = await response.text();
|
|
26931
|
+
const redirectMatch = source.match(/export\s+\*\s+from\s+["']([^"']+)["']/);
|
|
26932
|
+
if (redirectMatch) {
|
|
26933
|
+
const bundleUrl = `${ESM_SH_BASE_URL}${redirectMatch[1]}`;
|
|
26934
|
+
logger.debug(`[ExtensionLibraryLoader] Following redirect to ${bundleUrl}`);
|
|
26935
|
+
response = await fetchWithTimeout(bundleUrl);
|
|
26936
|
+
if (!response.ok) {
|
|
26937
|
+
throw new Error(`Failed to fetch bundle for ${librarySpec} from esm.sh: ${response.status} ${response.statusText}`);
|
|
26938
|
+
}
|
|
26939
|
+
source = await response.text();
|
|
26940
|
+
}
|
|
26941
|
+
await fs.mkdir(this.cacheDir, { recursive: true });
|
|
26942
|
+
await fs.writeFile(cachePath, source, "utf-8");
|
|
26943
|
+
await fs.writeFile(metaPath, JSON.stringify({ librarySpec, fetchedAt: (/* @__PURE__ */ new Date()).toISOString() }), "utf-8");
|
|
26944
|
+
logger.info(`[ExtensionLibraryLoader] Cached ${librarySpec}`);
|
|
26945
|
+
return source;
|
|
26946
|
+
}
|
|
26947
|
+
}
|
|
26966
26948
|
class ExtensionManager {
|
|
26967
26949
|
constructor(store, modelManager, eventManager, telemetryManager, memoryManager, registry = new ExtensionRegistry()) {
|
|
26968
26950
|
this.store = store;
|
|
@@ -26973,6 +26955,7 @@ class ExtensionManager {
|
|
|
26973
26955
|
this.registry = registry;
|
|
26974
26956
|
this.loader = new ExtensionLoader();
|
|
26975
26957
|
this.fetcher = new ExtensionFetcher();
|
|
26958
|
+
this.libraryLoader = new ExtensionLibraryLoader();
|
|
26976
26959
|
}
|
|
26977
26960
|
loader;
|
|
26978
26961
|
fetcher;
|
|
@@ -26980,6 +26963,7 @@ class ExtensionManager {
|
|
|
26980
26963
|
projectWatchers = /* @__PURE__ */ new Map();
|
|
26981
26964
|
initialized = false;
|
|
26982
26965
|
listeners = [];
|
|
26966
|
+
libraryLoader;
|
|
26983
26967
|
debouncedNotifyListeners = debounce(() => {
|
|
26984
26968
|
const extensions = this.registry.getExtensions();
|
|
26985
26969
|
for (const listener of this.listeners) {
|
|
@@ -27462,15 +27446,48 @@ class ExtensionManager {
|
|
|
27462
27446
|
errors
|
|
27463
27447
|
};
|
|
27464
27448
|
}
|
|
27449
|
+
getToolsInfo(projectDir) {
|
|
27450
|
+
const allExtensions = this.registry.getExtensions(projectDir);
|
|
27451
|
+
const extensions = this.filterEnabledExtensions(allExtensions);
|
|
27452
|
+
const result = [];
|
|
27453
|
+
for (const loaded of extensions) {
|
|
27454
|
+
const { instance, metadata } = loaded;
|
|
27455
|
+
if (!instance.getTools) {
|
|
27456
|
+
continue;
|
|
27457
|
+
}
|
|
27458
|
+
try {
|
|
27459
|
+
const context = new ExtensionContextImpl(loaded.id, metadata.name, this.store, this.modelManager, this.eventManager, this.memoryManager);
|
|
27460
|
+
const tools = instance.getTools(context, "agent", DEFAULT_AGENT_PROFILE);
|
|
27461
|
+
if (!Array.isArray(tools)) {
|
|
27462
|
+
continue;
|
|
27463
|
+
}
|
|
27464
|
+
const toolInfos = tools.filter((tool) => tool.name && tool.description).map((tool) => ({ name: tool.name, description: tool.description }));
|
|
27465
|
+
if (toolInfos.length > 0) {
|
|
27466
|
+
result.push({
|
|
27467
|
+
extensionId: loaded.id,
|
|
27468
|
+
extensionName: metadata.name,
|
|
27469
|
+
tools: toolInfos
|
|
27470
|
+
});
|
|
27471
|
+
}
|
|
27472
|
+
} catch (error) {
|
|
27473
|
+
logger.error(`[Extensions] Failed to get tools info from extension '${metadata.name}':`, error);
|
|
27474
|
+
}
|
|
27475
|
+
}
|
|
27476
|
+
return result;
|
|
27477
|
+
}
|
|
27465
27478
|
getTools(task, mode, profile) {
|
|
27466
27479
|
const collectedTools = [];
|
|
27467
27480
|
const allExtensions = this.registry.getExtensions(task.getProjectDir());
|
|
27468
27481
|
const extensions = this.filterEnabledExtensions(allExtensions);
|
|
27482
|
+
const disabledExtensionTools = profile.disabledExtensionTools ?? [];
|
|
27469
27483
|
for (const loaded of extensions) {
|
|
27470
27484
|
const { instance, metadata } = loaded;
|
|
27471
27485
|
if (!instance.getTools) {
|
|
27472
27486
|
continue;
|
|
27473
27487
|
}
|
|
27488
|
+
if (disabledExtensionTools.includes(loaded.id)) {
|
|
27489
|
+
continue;
|
|
27490
|
+
}
|
|
27474
27491
|
try {
|
|
27475
27492
|
const context = new ExtensionContextImpl(
|
|
27476
27493
|
loaded.id,
|
|
@@ -27493,6 +27510,10 @@ class ExtensionManager {
|
|
|
27493
27510
|
logger.error(`[Extensions] Invalid tool '${tool.name}' from extension '${metadata.name}': ${validation.errors.join(", ")}`);
|
|
27494
27511
|
continue;
|
|
27495
27512
|
}
|
|
27513
|
+
const fullToolId = `${loaded.id}${TOOL_GROUP_NAME_SEPARATOR}${tool.name}`;
|
|
27514
|
+
if (profile.toolApprovals?.[fullToolId] === ToolApprovalState.Never || profile.toolApprovals?.[tool.name] === ToolApprovalState.Never) {
|
|
27515
|
+
continue;
|
|
27516
|
+
}
|
|
27496
27517
|
collectedTools.push({
|
|
27497
27518
|
extensionId: loaded.id,
|
|
27498
27519
|
extensionName: metadata.name,
|
|
@@ -27516,11 +27537,12 @@ class ExtensionManager {
|
|
|
27516
27537
|
* @param abortSignal - Optional AbortSignal for cancellation support
|
|
27517
27538
|
* @returns A ToolSet containing all approved extension tools
|
|
27518
27539
|
*/
|
|
27519
|
-
createExtensionToolset(task, mode, profile, allTools, abortSignal) {
|
|
27540
|
+
createExtensionToolset(task, mode, profile, allTools, approvalManager, abortSignal) {
|
|
27520
27541
|
const toolSet = {};
|
|
27521
27542
|
const registeredTools = this.getTools(task, mode, profile);
|
|
27522
27543
|
for (const { extensionId, extensionName, tool } of registeredTools) {
|
|
27523
27544
|
const toolId = tool.name;
|
|
27545
|
+
const fullToolId = `${extensionId}${TOOL_GROUP_NAME_SEPARATOR}${tool.name}`;
|
|
27524
27546
|
const context = new ExtensionContextImpl(
|
|
27525
27547
|
extensionId,
|
|
27526
27548
|
extensionName,
|
|
@@ -27531,14 +27553,25 @@ class ExtensionManager {
|
|
|
27531
27553
|
task.project,
|
|
27532
27554
|
task
|
|
27533
27555
|
);
|
|
27534
|
-
if (profile.toolApprovals?.[toolId] === ToolApprovalState.Never) {
|
|
27535
|
-
logger.debug(`[Extensions] Skipping tool '${tool.name}' (marked as Never approved)`);
|
|
27536
|
-
continue;
|
|
27537
|
-
}
|
|
27538
27556
|
toolSet[toolId] = {
|
|
27539
27557
|
description: tool.description,
|
|
27540
27558
|
inputSchema: tool.inputSchema,
|
|
27541
27559
|
execute: async (input, options) => {
|
|
27560
|
+
const toolApproval = profile.toolApprovals?.[fullToolId];
|
|
27561
|
+
logger.debug(
|
|
27562
|
+
`[Extensions] Tool '${tool.name}' approval check: fullToolId='${fullToolId}', approval=${toolApproval}, allApprovals=${JSON.stringify(profile.toolApprovals)}`
|
|
27563
|
+
);
|
|
27564
|
+
if (toolApproval === ToolApprovalState.Ask) {
|
|
27565
|
+
const questionKey = fullToolId;
|
|
27566
|
+
const questionText = `Approve tool ${tool.name} from ${extensionName} extension?`;
|
|
27567
|
+
const questionSubject = input ? JSON.stringify(input) : void 0;
|
|
27568
|
+
const [isApproved, userInput] = await approvalManager.handleToolApproval(fullToolId, input, questionKey, questionText, questionSubject);
|
|
27569
|
+
if (!isApproved) {
|
|
27570
|
+
logger.warn(`Tool execution denied by user: ${fullToolId}`);
|
|
27571
|
+
return `Tool execution denied by user.${userInput ? ` User input: ${userInput}` : ""}`;
|
|
27572
|
+
}
|
|
27573
|
+
logger.debug(`Tool execution approved: ${fullToolId}`);
|
|
27574
|
+
}
|
|
27542
27575
|
const allToolsInternal = Object.entries(allTools).reduce(
|
|
27543
27576
|
(acc, [toolId2, tool2]) => {
|
|
27544
27577
|
acc[toolId2] = {
|
|
@@ -27834,6 +27867,39 @@ class ExtensionManager {
|
|
|
27834
27867
|
}
|
|
27835
27868
|
return collectedComponents;
|
|
27836
27869
|
}
|
|
27870
|
+
getUIComponentsLibraries(project) {
|
|
27871
|
+
const librariesByExtension = /* @__PURE__ */ new Map();
|
|
27872
|
+
const allExtensions = this.registry.getExtensions(project?.baseDir);
|
|
27873
|
+
const extensions = this.filterEnabledExtensions(allExtensions);
|
|
27874
|
+
for (const loaded of extensions) {
|
|
27875
|
+
const { instance, initialized, metadata } = loaded;
|
|
27876
|
+
if (!initialized || !instance.getUIComponentsLibraries) {
|
|
27877
|
+
continue;
|
|
27878
|
+
}
|
|
27879
|
+
try {
|
|
27880
|
+
const libraries = instance.getUIComponentsLibraries();
|
|
27881
|
+
if (typeof libraries !== "object" || libraries === null || Array.isArray(libraries)) {
|
|
27882
|
+
logger.error(`[Extensions] Extension '${metadata.name}' getUIComponentsLibraries() did not return a Record<string, string>`);
|
|
27883
|
+
continue;
|
|
27884
|
+
}
|
|
27885
|
+
const validLibs = {};
|
|
27886
|
+
for (const [key, spec] of Object.entries(libraries)) {
|
|
27887
|
+
if (typeof key === "string" && typeof spec === "string") {
|
|
27888
|
+
validLibs[key] = spec;
|
|
27889
|
+
}
|
|
27890
|
+
}
|
|
27891
|
+
if (Object.keys(validLibs).length > 0) {
|
|
27892
|
+
librariesByExtension.set(loaded.id, validLibs);
|
|
27893
|
+
}
|
|
27894
|
+
} catch (error) {
|
|
27895
|
+
logger.error(`[Extensions] Failed to get UI component libraries from extension '${metadata.name}':`, error);
|
|
27896
|
+
}
|
|
27897
|
+
}
|
|
27898
|
+
return librariesByExtension;
|
|
27899
|
+
}
|
|
27900
|
+
async loadExtensionLibrary(librarySpec) {
|
|
27901
|
+
return await this.libraryLoader.loadLibrary(librarySpec);
|
|
27902
|
+
}
|
|
27837
27903
|
/**
|
|
27838
27904
|
* Check if an extension provides a settings config component.
|
|
27839
27905
|
* Uses the dedicated getConfigComponent() method on the Extension interface.
|
|
@@ -28743,12 +28809,26 @@ class EventsHandler {
|
|
|
28743
28809
|
}
|
|
28744
28810
|
await task.mergeWorktreeToMain(squash, targetBranch, commitMessage);
|
|
28745
28811
|
}
|
|
28746
|
-
async
|
|
28812
|
+
async switchToLocalWorkingMode(baseDir, taskId, options) {
|
|
28747
28813
|
const task = this.projectManager.getProject(baseDir).getTask(taskId);
|
|
28748
28814
|
if (!task) {
|
|
28749
28815
|
throw new Error(`Task ${taskId} not found`);
|
|
28750
28816
|
}
|
|
28751
|
-
await task.
|
|
28817
|
+
await task.switchToLocalWorkingMode(options);
|
|
28818
|
+
}
|
|
28819
|
+
async switchToWorktreeWorkingMode(baseDir, taskId, options) {
|
|
28820
|
+
const task = this.projectManager.getProject(baseDir).getTask(taskId);
|
|
28821
|
+
if (!task) {
|
|
28822
|
+
throw new Error(`Task ${taskId} not found`);
|
|
28823
|
+
}
|
|
28824
|
+
await task.switchToWorktreeWorkingMode(options);
|
|
28825
|
+
}
|
|
28826
|
+
async getLocalUncommittedFiles(baseDir, taskId) {
|
|
28827
|
+
const task = this.projectManager.getProject(baseDir).getTask(taskId);
|
|
28828
|
+
if (!task) {
|
|
28829
|
+
throw new Error(`Task ${taskId} not found`);
|
|
28830
|
+
}
|
|
28831
|
+
return await task.getLocalUncommittedFiles();
|
|
28752
28832
|
}
|
|
28753
28833
|
async applyUncommittedChanges(baseDir, taskId, targetBranch) {
|
|
28754
28834
|
const task = this.projectManager.getProject(baseDir).getTask(taskId);
|
|
@@ -29227,6 +29307,9 @@ ${error instanceof Error ? error.message : String(error)}`);
|
|
|
29227
29307
|
readmeContent: ext.readmeContent
|
|
29228
29308
|
}));
|
|
29229
29309
|
}
|
|
29310
|
+
getExtensionToolsInfo(projectDir) {
|
|
29311
|
+
return this.extensionManager.getToolsInfo(projectDir);
|
|
29312
|
+
}
|
|
29230
29313
|
async getAvailableExtensions(repositories, forceRefresh, fetchOnly) {
|
|
29231
29314
|
return await this.extensionManager.getAvailableExtensions(repositories, forceRefresh, fetchOnly);
|
|
29232
29315
|
}
|
|
@@ -29258,15 +29341,21 @@ ${error instanceof Error ? error.message : String(error)}`);
|
|
|
29258
29341
|
const task = taskId && project ? project.getTask(taskId) ?? void 0 : void 0;
|
|
29259
29342
|
const components = this.extensionManager.getUIComponents(project, task);
|
|
29260
29343
|
const filtered = placement ? components.filter((c) => c.component.placement === placement) : components;
|
|
29344
|
+
const librariesByExtension = this.extensionManager.getUIComponentsLibraries(project);
|
|
29261
29345
|
return filtered.map((c) => ({
|
|
29262
29346
|
extensionId: c.extensionId,
|
|
29263
29347
|
componentId: c.component.id,
|
|
29348
|
+
name: c.component.name,
|
|
29264
29349
|
placement: c.component.placement,
|
|
29265
29350
|
jsx: c.component.jsx,
|
|
29266
29351
|
loadData: c.component.loadData,
|
|
29267
|
-
noDataCache: c.component.noDataCache
|
|
29352
|
+
noDataCache: c.component.noDataCache,
|
|
29353
|
+
libraries: librariesByExtension.get(c.extensionId)
|
|
29268
29354
|
}));
|
|
29269
29355
|
}
|
|
29356
|
+
async loadExtensionLibrary(librarySpec) {
|
|
29357
|
+
return await this.extensionManager.loadExtensionLibrary(librarySpec);
|
|
29358
|
+
}
|
|
29270
29359
|
async getUIExtensionData(extensionId, componentId, projectDir, taskId) {
|
|
29271
29360
|
logger.debug("Getting UI extension data:", {
|
|
29272
29361
|
extensionId,
|
|
@@ -30596,6 +30685,9 @@ const migrateSettingsV19toV20 = (settings) => {
|
|
|
30596
30685
|
}
|
|
30597
30686
|
};
|
|
30598
30687
|
};
|
|
30688
|
+
const migrateProvidersV20toV21 = (providers) => {
|
|
30689
|
+
return providers.filter((p) => p.provider.name !== "claude-agent-sdk" && p.provider.name !== "auggie");
|
|
30690
|
+
};
|
|
30599
30691
|
const DEFAULT_SETTINGS = {
|
|
30600
30692
|
language: "en",
|
|
30601
30693
|
startupMode: ProjectStartMode.Empty,
|
|
@@ -30675,7 +30767,7 @@ const DEFAULT_SETTINGS = {
|
|
|
30675
30767
|
const compareBaseDirs = (baseDir1, baseDir2) => {
|
|
30676
30768
|
return normalizeBaseDir(baseDir1) === normalizeBaseDir(baseDir2);
|
|
30677
30769
|
};
|
|
30678
|
-
const CURRENT_SETTINGS_VERSION =
|
|
30770
|
+
const CURRENT_SETTINGS_VERSION = 21;
|
|
30679
30771
|
class Store {
|
|
30680
30772
|
// @ts-expect-error expected to be initialized
|
|
30681
30773
|
store;
|
|
@@ -30830,6 +30922,10 @@ class Store {
|
|
|
30830
30922
|
settings = migrateSettingsV19toV20(settings);
|
|
30831
30923
|
settingsVersion = 20;
|
|
30832
30924
|
}
|
|
30925
|
+
if (settingsVersion === 20) {
|
|
30926
|
+
providers = migrateProvidersV20toV21(providers || []);
|
|
30927
|
+
settingsVersion = 21;
|
|
30928
|
+
}
|
|
30833
30929
|
this.store.set("settings", settings);
|
|
30834
30930
|
this.store.set("openProjects", openProjects || []);
|
|
30835
30931
|
this.store.set("providers", providers || []);
|