@kafca/agentdock 0.1.29 → 0.1.31
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/README.md +4 -0
- package/dist/renderer/assets/{Badge-ngf0eCzI.js → Badge-DaHt-aUT.js} +1 -1
- package/dist/renderer/assets/{Chat-tCGY5odh.js → Chat-Dzeq3kiD.js} +1 -1
- package/dist/renderer/assets/{ChatMarkdown-vqDWgVNb.js → ChatMarkdown-B-L5Roai.js} +1 -1
- package/dist/renderer/assets/{Config-YsVDQmIs.js → Config-BI4LJ7Fw.js} +1 -1
- package/dist/renderer/assets/{CronList-DQN0T7Yc.js → CronList-Dic7pblj.js} +1 -1
- package/dist/renderer/assets/{Dashboard-C2O6Yxq3.js → Dashboard-C0_ATyGe.js} +2 -2
- package/dist/renderer/assets/{EmptyState-CTkA-fBQ.js → EmptyState-SQsG1DZP.js} +1 -1
- package/dist/renderer/assets/{KnowledgeDetail-DjLZDItQ.js → KnowledgeDetail-D4yUJzp7.js} +1 -1
- package/dist/renderer/assets/{KnowledgeHome-2NHeRZxW.js → KnowledgeHome-L0tsg-oo.js} +1 -1
- package/dist/renderer/assets/{Logs-CQ6j-Sct.js → Logs-C2Jdr3uQ.js} +1 -1
- package/dist/renderer/assets/{Modal-9g1uWJfC.js → Modal-GUH3iPXo.js} +1 -1
- package/dist/renderer/assets/{Page-B4mPLn6n.js → Page-m42FBy97.js} +1 -1
- package/dist/renderer/assets/{ProjectDetail-pBXOAeL4.js → ProjectDetail-RF_sagPO.js} +1 -1
- package/dist/renderer/assets/{ProjectList-B9PYfZaS.js → ProjectList-Cyr8RDK3.js} +1 -1
- package/dist/renderer/assets/{Select-BWFQJ2R8.js → Select-CRlDgI5s.js} +1 -1
- package/dist/renderer/assets/{SessionChat-fBrzJs3A.js → SessionChat-_HhzMwEO.js} +1 -1
- package/dist/renderer/assets/{SessionList-DjHOsk7X.js → SessionList-DNwZjGTv.js} +1 -1
- package/dist/renderer/assets/ThreadChat-DxBmdsAm.js +23 -0
- package/dist/renderer/assets/{Workspace-nfTcxlhw.js → Workspace-DFphG85O.js} +1 -1
- package/dist/renderer/assets/{arrow-left-CIWZ6JEB.js → arrow-left-bILMzse7.js} +1 -1
- package/dist/renderer/assets/{book-open-Ck6BgBhN.js → book-open-BNBWEEve.js} +1 -1
- package/dist/renderer/assets/{check-CtB2ZLVE.js → check-MGp5kvnb.js} +1 -1
- package/dist/renderer/assets/{chevron-down--8lODnN0.js → chevron-down-zsfoTlh7.js} +1 -1
- package/dist/renderer/assets/{circle-CKQOJcbh.js → circle-BX_xUSg-.js} +1 -1
- package/dist/renderer/assets/{desktop-Do2I28CT.js → desktop-CgrO_cdQ.js} +1 -1
- package/dist/renderer/assets/{desktop-BkMW-h5p.js → desktop-O8_6ZCVZ.js} +2 -2
- package/dist/renderer/assets/{funnel-CkZuFIwa.js → funnel-7442U1wq.js} +1 -1
- package/dist/renderer/assets/{heart-CAX_CqFQ.js → heart-B3d8bnSH.js} +1 -1
- package/dist/renderer/assets/{index--_L0Y77h.js → index-5YUqCvBf.js} +1 -1
- package/dist/renderer/assets/{index-DvAYflFj.js → index-BBaYsVjU.js} +2 -2
- package/dist/renderer/assets/{pencil-sIRhtchu.js → pencil-QzWgkmoH.js} +1 -1
- package/dist/renderer/assets/{play-CJNRbCL5.js → play-Bsc8hSI7.js} +1 -1
- package/dist/renderer/assets/{plug-DsFe9GBx.js → plug-CRY7sjvB.js} +1 -1
- package/dist/renderer/assets/{plus-KDwEI-Rs.js → plus-Dr5Ei8Ud.js} +1 -1
- package/dist/renderer/assets/projects-BDYSOFIJ.js +1 -0
- package/dist/renderer/assets/{save-C-p5r3K-.js → save-giJnp2Ki.js} +1 -1
- package/dist/renderer/assets/{search-BZxQJb2k.js → search-DcvHLmKs.js} +1 -1
- package/dist/renderer/assets/{server-BV-K022I.js → server-D_Qu8If5.js} +1 -1
- package/dist/renderer/assets/{session-utils-ClQTa8yS.js → session-utils-CsASahfU.js} +1 -1
- package/dist/renderer/assets/{sessions-B0FSCA9O.js → sessions-eMpPqp4P.js} +1 -1
- package/dist/renderer/assets/{shield-check-B6AjkXUd.js → shield-check-BpF0uIw-.js} +1 -1
- package/dist/renderer/assets/{trash-2-41Pv4qRx.js → trash-2-OJFmx3xk.js} +1 -1
- package/dist/renderer/assets/{user-NKKHCKm9.js → user-GL_ivaV6.js} +1 -1
- package/dist/renderer/assets/{wifi-off-E1ZNhLG5.js → wifi-off-CQT5VNQl.js} +1 -1
- package/dist/renderer/index.html +1 -1
- package/dist-electron/electron/agent-runtime-detector.test.js +30 -0
- package/dist-electron/electron/local-core-refactor.test.js +749 -44
- package/dist-electron/electron/plugin-kernel.test.js +81 -1
- package/dist-electron/electron/workspace-task-store.test.js +7 -1
- package/dist-electron/services/local-ai-core/src/acp/local-core-acp-backend.js +34 -4
- package/dist-electron/services/local-ai-core/src/acp/local-core-acp-progress.js +239 -7
- package/dist-electron/services/local-ai-core/src/acp/local-core-acp-session-coordinator.js +10 -6
- package/dist-electron/services/local-ai-core/src/acp/local-core-acp-transport.js +1 -0
- package/dist-electron/services/local-ai-core/src/acp/local-core-acp-turn-coordinator.js +169 -5
- package/dist-electron/services/local-ai-core/src/agents/claudecode/behavior.js +5 -0
- package/dist-electron/services/local-ai-core/src/agents/claudecode/definition.js +36 -0
- package/dist-electron/services/local-ai-core/src/agents/claudecode/index.js +15 -0
- package/dist-electron/services/local-ai-core/src/agents/codex/behavior.js +5 -0
- package/dist-electron/services/local-ai-core/src/agents/codex/definition.js +24 -0
- package/dist-electron/services/local-ai-core/src/agents/codex/index.js +15 -0
- package/dist-electron/services/local-ai-core/src/agents/hermes/behavior.js +29 -0
- package/dist-electron/services/local-ai-core/src/agents/hermes/definition.js +22 -0
- package/dist-electron/services/local-ai-core/src/agents/hermes/index.js +15 -0
- package/dist-electron/services/local-ai-core/src/agents/index.js +98 -0
- package/dist-electron/services/local-ai-core/src/agents/localcore-acp/behavior.js +5 -0
- package/dist-electron/services/local-ai-core/src/agents/localcore-acp/definition.js +14 -0
- package/dist-electron/services/local-ai-core/src/agents/localcore-acp/index.js +27 -0
- package/dist-electron/services/local-ai-core/src/agents/opencode/behavior.js +5 -0
- package/dist-electron/services/local-ai-core/src/agents/opencode/definition.js +18 -0
- package/dist-electron/services/local-ai-core/src/agents/opencode/index.js +15 -0
- package/dist-electron/services/local-ai-core/src/agents/opencode/launch.js +119 -0
- package/dist-electron/services/local-ai-core/src/agents/pi/behavior.js +5 -0
- package/dist-electron/services/local-ai-core/src/agents/pi/definition.js +23 -0
- package/dist-electron/services/local-ai-core/src/agents/pi/index.js +15 -0
- package/dist-electron/services/local-ai-core/src/agents/pi/launch.js +139 -0
- package/dist-electron/services/local-ai-core/src/agents/shared/acp-behavior.js +11 -0
- package/dist-electron/services/local-ai-core/src/agents/shared/agent-plugin.js +60 -0
- package/dist-electron/services/local-ai-core/src/agents/shared/definition.js +12 -0
- package/dist-electron/services/local-ai-core/src/agents/shared/launch-utils.js +122 -0
- package/dist-electron/services/local-ai-core/src/agents/shared/progress-replay.js +19 -0
- package/dist-electron/services/local-ai-core/src/agents/shared/replay-prefix.js +68 -0
- package/dist-electron/services/local-ai-core/src/channel/lark/local-core-lark-gateway.js +0 -2
- package/dist-electron/services/local-ai-core/src/channel/lark/runtime-state.js +1 -1
- package/dist-electron/services/local-ai-core/src/channel/weixin/local-core-weixin-gateway.js +13 -2
- package/dist-electron/services/local-ai-core/src/kernel/bootstrap.js +8 -7
- package/dist-electron/services/local-ai-core/src/plugins/builtin/agent-localcore-acp-plugin.js +9 -130
- package/dist-electron/services/local-ai-core/src/router/workspace-route-config.js +22 -397
- package/dist-electron/services/local-ai-core/src/runtime/agent-runtime-detector.js +9 -45
- package/dist-electron/services/local-ai-core/src/runtime/local-core-runtime-state.js +62 -1
- package/dist-electron/services/local-ai-core/src/runtime/runtime-detection-service.js +2 -12
- package/dist-electron/shared/desktop.js +3 -1
- package/dist-electron/src/pages/Threads/thread-chat-model.js +27 -18
- package/dist-electron/src/pages/Threads/thread-chat-permission.test.js +57 -18
- package/package.json +1 -1
- package/dist/renderer/assets/ThreadChat-MagPeJD0.js +0 -23
- package/dist/renderer/assets/projects-CJUs2vaq.js +0 -1
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.resolveOpencodeModel = resolveOpencodeModel;
|
|
4
|
+
exports.buildOpencodeLaunchConfig = buildOpencodeLaunchConfig;
|
|
5
|
+
const desktop_js_1 = require("../../../../../shared/desktop.js");
|
|
6
|
+
const launch_utils_js_1 = require("../shared/launch-utils.js");
|
|
7
|
+
function resolveOpencodeModel(input) {
|
|
8
|
+
const configuredProviderModel = getFirstProviderModelRef(input.providers);
|
|
9
|
+
if (configuredProviderModel &&
|
|
10
|
+
(!input.rawModel || input.normalizedModel === desktop_js_1.DEFAULT_DESKTOP_OPENCODE_MODEL)) {
|
|
11
|
+
return configuredProviderModel;
|
|
12
|
+
}
|
|
13
|
+
return input.normalizedModel;
|
|
14
|
+
}
|
|
15
|
+
function buildOpencodeLaunchConfig(model, providers) {
|
|
16
|
+
const inlineConfig = buildOpencodeInlineConfig(model, providers);
|
|
17
|
+
return {
|
|
18
|
+
command: 'opencode',
|
|
19
|
+
args: ['acp'],
|
|
20
|
+
env: {
|
|
21
|
+
...(inlineConfig.env || {}),
|
|
22
|
+
OPENCODE_CONFIG_CONTENT: JSON.stringify(inlineConfig.config || { $schema: 'https://opencode.ai/config.json' }),
|
|
23
|
+
},
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
function getFirstProviderModelRef(providers) {
|
|
27
|
+
for (const provider of providers) {
|
|
28
|
+
const providerId = normalizeOpencodeProviderId(provider.name);
|
|
29
|
+
const modelId = (0, launch_utils_js_1.getProviderDefaultModelId)(provider);
|
|
30
|
+
if (providerId && modelId) {
|
|
31
|
+
return `${providerId}/${modelId}`;
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
return '';
|
|
35
|
+
}
|
|
36
|
+
function buildOpencodeInlineConfig(model, providers) {
|
|
37
|
+
const config = {
|
|
38
|
+
$schema: 'https://opencode.ai/config.json',
|
|
39
|
+
};
|
|
40
|
+
const env = {};
|
|
41
|
+
if (model) {
|
|
42
|
+
config.model = model;
|
|
43
|
+
}
|
|
44
|
+
const providerConfig = {};
|
|
45
|
+
for (const provider of providers) {
|
|
46
|
+
const providerId = normalizeOpencodeProviderId(provider.name);
|
|
47
|
+
if (!providerId) {
|
|
48
|
+
continue;
|
|
49
|
+
}
|
|
50
|
+
const entry = {
|
|
51
|
+
name: String(provider.name || providerId),
|
|
52
|
+
};
|
|
53
|
+
if (shouldUseOpenAiCompatibleProvider(providerId)) {
|
|
54
|
+
entry.npm = '@ai-sdk/openai-compatible';
|
|
55
|
+
}
|
|
56
|
+
const options = {};
|
|
57
|
+
const baseUrl = String(provider.base_url || '').trim();
|
|
58
|
+
if (baseUrl) {
|
|
59
|
+
options.baseURL = baseUrl;
|
|
60
|
+
}
|
|
61
|
+
const apiKey = String(provider.api_key || '').trim();
|
|
62
|
+
if (apiKey) {
|
|
63
|
+
const envName = opencodeProviderApiKeyEnvName(providerId);
|
|
64
|
+
env[envName] = apiKey;
|
|
65
|
+
options.apiKey = `{env:${envName}}`;
|
|
66
|
+
}
|
|
67
|
+
if (Object.keys(options).length > 0) {
|
|
68
|
+
entry.options = options;
|
|
69
|
+
}
|
|
70
|
+
const models = buildOpencodeProviderModels(provider);
|
|
71
|
+
if (Object.keys(models).length > 0) {
|
|
72
|
+
entry.models = models;
|
|
73
|
+
}
|
|
74
|
+
providerConfig[providerId] = entry;
|
|
75
|
+
}
|
|
76
|
+
if (Object.keys(providerConfig).length > 0) {
|
|
77
|
+
config.provider = providerConfig;
|
|
78
|
+
}
|
|
79
|
+
return {
|
|
80
|
+
config,
|
|
81
|
+
env,
|
|
82
|
+
};
|
|
83
|
+
}
|
|
84
|
+
function buildOpencodeProviderModels(provider) {
|
|
85
|
+
const models = {};
|
|
86
|
+
const addModel = (model, alias) => {
|
|
87
|
+
const modelId = String(model || '').trim();
|
|
88
|
+
if (!modelId || models[modelId]) {
|
|
89
|
+
return;
|
|
90
|
+
}
|
|
91
|
+
models[modelId] = {
|
|
92
|
+
name: String(alias || modelId).trim() || modelId,
|
|
93
|
+
};
|
|
94
|
+
};
|
|
95
|
+
addModel(provider.model);
|
|
96
|
+
for (const model of Array.isArray(provider.models) ? provider.models : []) {
|
|
97
|
+
addModel(model?.model, model?.alias);
|
|
98
|
+
}
|
|
99
|
+
return models;
|
|
100
|
+
}
|
|
101
|
+
function normalizeOpencodeProviderId(value) {
|
|
102
|
+
return String(value || '')
|
|
103
|
+
.trim()
|
|
104
|
+
.toLowerCase()
|
|
105
|
+
.replace(/[^a-z0-9._-]+/g, '-')
|
|
106
|
+
.replace(/^-+|-+$/g, '');
|
|
107
|
+
}
|
|
108
|
+
function opencodeProviderApiKeyEnvName(providerId) {
|
|
109
|
+
const suffix = providerId.toUpperCase().replace(/[^A-Z0-9]+/g, '_').replace(/^_+|_+$/g, '');
|
|
110
|
+
return `AI_WORKSTATION_OPENCODE_${suffix || 'PROVIDER'}_API_KEY`;
|
|
111
|
+
}
|
|
112
|
+
function shouldUseOpenAiCompatibleProvider(providerId) {
|
|
113
|
+
const builtInNonCompatibleProviders = new Set([
|
|
114
|
+
'anthropic',
|
|
115
|
+
'google',
|
|
116
|
+
'gemini',
|
|
117
|
+
]);
|
|
118
|
+
return !builtInNonCompatibleProviders.has(providerId);
|
|
119
|
+
}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.piAgentDefinition = void 0;
|
|
4
|
+
const desktop_js_1 = require("../../../../../shared/desktop.js");
|
|
5
|
+
const behavior_js_1 = require("./behavior.js");
|
|
6
|
+
const launch_js_1 = require("./launch.js");
|
|
7
|
+
exports.piAgentDefinition = {
|
|
8
|
+
agentType: 'pi',
|
|
9
|
+
displayName: 'Pi',
|
|
10
|
+
behavior: behavior_js_1.piAcpBehavior,
|
|
11
|
+
detection: {
|
|
12
|
+
commandCandidates: ['pi'],
|
|
13
|
+
versionArgs: ['--version'],
|
|
14
|
+
bundledRuntimes: [
|
|
15
|
+
{
|
|
16
|
+
packageName: desktop_js_1.DESKTOP_PI_CODING_AGENT_PACKAGE,
|
|
17
|
+
candidates: ['dist/cli.js'],
|
|
18
|
+
},
|
|
19
|
+
],
|
|
20
|
+
},
|
|
21
|
+
resolveModel: launch_js_1.resolvePiModel,
|
|
22
|
+
buildLaunchConfig: launch_js_1.buildPiLaunchConfig,
|
|
23
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.piAgentDefinition = exports.piAcpBehavior = void 0;
|
|
4
|
+
exports.createBuiltinPiAgentPlugin = createBuiltinPiAgentPlugin;
|
|
5
|
+
const agent_plugin_js_1 = require("../shared/agent-plugin.js");
|
|
6
|
+
const behavior_js_1 = require("./behavior.js");
|
|
7
|
+
Object.defineProperty(exports, "piAcpBehavior", { enumerable: true, get: function () { return behavior_js_1.piAcpBehavior; } });
|
|
8
|
+
const definition_js_1 = require("./definition.js");
|
|
9
|
+
Object.defineProperty(exports, "piAgentDefinition", { enumerable: true, get: function () { return definition_js_1.piAgentDefinition; } });
|
|
10
|
+
function createBuiltinPiAgentPlugin() {
|
|
11
|
+
return (0, agent_plugin_js_1.createBuiltinAgentPlugin)({
|
|
12
|
+
definition: definition_js_1.piAgentDefinition,
|
|
13
|
+
match: (normalizedAgentType) => normalizedAgentType === 'pi',
|
|
14
|
+
});
|
|
15
|
+
}
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.resolvePiModel = resolvePiModel;
|
|
4
|
+
exports.buildPiLaunchConfig = buildPiLaunchConfig;
|
|
5
|
+
const node_path_1 = require("node:path");
|
|
6
|
+
const desktop_js_1 = require("../../../../../shared/desktop.js");
|
|
7
|
+
const launch_utils_js_1 = require("../shared/launch-utils.js");
|
|
8
|
+
function resolvePiModel(input) {
|
|
9
|
+
return input.rawModel || (0, launch_utils_js_1.getFirstProviderModelId)(input.providers);
|
|
10
|
+
}
|
|
11
|
+
function buildPiLaunchConfig(input) {
|
|
12
|
+
const bundledPiAcp = (0, launch_utils_js_1.resolveBundledAcpCommand)(desktop_js_1.DESKTOP_PI_ACP_PACKAGE, 'pi-acp');
|
|
13
|
+
const bundledPiCommand = (0, launch_utils_js_1.resolveBundledAcpCommand)(desktop_js_1.DESKTOP_PI_CODING_AGENT_PACKAGE, 'pi').args[0];
|
|
14
|
+
return {
|
|
15
|
+
command: bundledPiAcp.command,
|
|
16
|
+
args: [...bundledPiAcp.args],
|
|
17
|
+
env: {
|
|
18
|
+
...collectPiProviderEnv(input.providers),
|
|
19
|
+
...writePiProviderRuntimeConfig(input),
|
|
20
|
+
PI_ACP_PI_COMMAND: bundledPiCommand,
|
|
21
|
+
},
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
function collectPiProviderEnv(providers) {
|
|
25
|
+
const env = {};
|
|
26
|
+
for (const provider of providers) {
|
|
27
|
+
const apiKey = String(provider.api_key || '').trim();
|
|
28
|
+
const envName = piProviderApiKeyEnvName(provider.name);
|
|
29
|
+
if (apiKey && envName) {
|
|
30
|
+
env[envName] = apiKey;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
return env;
|
|
34
|
+
}
|
|
35
|
+
function writePiProviderRuntimeConfig(input) {
|
|
36
|
+
if (input.providers.length === 0) {
|
|
37
|
+
return {};
|
|
38
|
+
}
|
|
39
|
+
const { providerId, modelId } = resolvePiProviderModel(input.providers, input.model);
|
|
40
|
+
const agentDir = (0, launch_utils_js_1.projectLocalStateDir)(input.configState, '.pi-agent', input.project.name);
|
|
41
|
+
(0, launch_utils_js_1.ensurePrivateDir)(agentDir);
|
|
42
|
+
const auth = {};
|
|
43
|
+
const modelProviders = {};
|
|
44
|
+
for (const provider of input.providers) {
|
|
45
|
+
const id = normalizePiProviderId(provider.name);
|
|
46
|
+
if (!id) {
|
|
47
|
+
continue;
|
|
48
|
+
}
|
|
49
|
+
const apiKey = String(provider.api_key || '').trim();
|
|
50
|
+
const baseUrl = String(provider.base_url || '').trim();
|
|
51
|
+
if (apiKey) {
|
|
52
|
+
auth[id] = { type: 'api_key', key: apiKey };
|
|
53
|
+
}
|
|
54
|
+
if (baseUrl || apiKey) {
|
|
55
|
+
modelProviders[id] = {
|
|
56
|
+
name: String(provider.name || id).trim() || id,
|
|
57
|
+
...(baseUrl ? { baseUrl } : {}),
|
|
58
|
+
...(apiKey ? { apiKey } : {}),
|
|
59
|
+
};
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
(0, launch_utils_js_1.writeJsonFile)((0, node_path_1.resolve)(agentDir, 'auth.json'), auth);
|
|
63
|
+
(0, launch_utils_js_1.writeJsonFile)((0, node_path_1.resolve)(agentDir, 'models.json'), { providers: modelProviders });
|
|
64
|
+
(0, launch_utils_js_1.writeJsonFile)((0, node_path_1.resolve)(agentDir, 'settings.json'), {
|
|
65
|
+
...(providerId ? { defaultProvider: providerId } : {}),
|
|
66
|
+
...(modelId ? { defaultModel: modelId } : {}),
|
|
67
|
+
quietStartup: true,
|
|
68
|
+
}, 0o644);
|
|
69
|
+
return {
|
|
70
|
+
PI_CODING_AGENT_DIR: agentDir,
|
|
71
|
+
};
|
|
72
|
+
}
|
|
73
|
+
function resolvePiProviderModel(providers, model) {
|
|
74
|
+
const [explicitProvider, explicitModel] = (0, launch_utils_js_1.splitProviderModelRef)(model);
|
|
75
|
+
if (explicitProvider && explicitModel) {
|
|
76
|
+
return {
|
|
77
|
+
providerId: normalizePiProviderId(explicitProvider),
|
|
78
|
+
modelId: explicitModel,
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
for (const provider of providers) {
|
|
82
|
+
const providerId = normalizePiProviderId(provider.name);
|
|
83
|
+
const modelId = (0, launch_utils_js_1.getProviderDefaultModelId)(provider);
|
|
84
|
+
if (providerId && modelId && (!model || model === modelId)) {
|
|
85
|
+
return { providerId, modelId };
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
const fallbackProvider = providers.find((provider) => normalizePiProviderId(provider.name));
|
|
89
|
+
return {
|
|
90
|
+
providerId: normalizePiProviderId(fallbackProvider?.name),
|
|
91
|
+
modelId: model,
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
function normalizePiProviderId(providerName) {
|
|
95
|
+
const providerId = (0, launch_utils_js_1.normalizeProviderId)(providerName);
|
|
96
|
+
const aliases = {
|
|
97
|
+
google: 'google',
|
|
98
|
+
gemini: 'google',
|
|
99
|
+
kimi: 'kimi-coding',
|
|
100
|
+
moonshot: 'moonshotai',
|
|
101
|
+
zhipuai: 'zai',
|
|
102
|
+
};
|
|
103
|
+
return aliases[providerId] || providerId;
|
|
104
|
+
}
|
|
105
|
+
function piProviderApiKeyEnvName(providerName) {
|
|
106
|
+
const providerId = (0, launch_utils_js_1.normalizeProviderId)(providerName);
|
|
107
|
+
const envNames = {
|
|
108
|
+
anthropic: 'ANTHROPIC_API_KEY',
|
|
109
|
+
'azure-openai': 'AZURE_OPENAI_API_KEY',
|
|
110
|
+
'azure-openai-responses': 'AZURE_OPENAI_API_KEY',
|
|
111
|
+
cerebras: 'CEREBRAS_API_KEY',
|
|
112
|
+
cloudflare: 'CLOUDFLARE_API_KEY',
|
|
113
|
+
'cloudflare-ai-gateway': 'CLOUDFLARE_API_KEY',
|
|
114
|
+
'cloudflare-workers-ai': 'CLOUDFLARE_API_KEY',
|
|
115
|
+
deepseek: 'DEEPSEEK_API_KEY',
|
|
116
|
+
fireworks: 'FIREWORKS_API_KEY',
|
|
117
|
+
gemini: 'GEMINI_API_KEY',
|
|
118
|
+
google: 'GEMINI_API_KEY',
|
|
119
|
+
groq: 'GROQ_API_KEY',
|
|
120
|
+
huggingface: 'HF_TOKEN',
|
|
121
|
+
kimi: 'KIMI_API_KEY',
|
|
122
|
+
'kimi-coding': 'KIMI_API_KEY',
|
|
123
|
+
minimax: 'MINIMAX_API_KEY',
|
|
124
|
+
'minimax-cn': 'MINIMAX_CN_API_KEY',
|
|
125
|
+
mistral: 'MISTRAL_API_KEY',
|
|
126
|
+
moonshot: 'KIMI_API_KEY',
|
|
127
|
+
openai: 'OPENAI_API_KEY',
|
|
128
|
+
opencode: 'OPENCODE_API_KEY',
|
|
129
|
+
'opencode-go': 'OPENCODE_API_KEY',
|
|
130
|
+
openrouter: 'OPENROUTER_API_KEY',
|
|
131
|
+
siliconflow: 'SILICONFLOW_API_KEY',
|
|
132
|
+
vercel: 'AI_GATEWAY_API_KEY',
|
|
133
|
+
'vercel-ai-gateway': 'AI_GATEWAY_API_KEY',
|
|
134
|
+
xai: 'XAI_API_KEY',
|
|
135
|
+
zai: 'ZAI_API_KEY',
|
|
136
|
+
zhipuai: 'ZAI_API_KEY',
|
|
137
|
+
};
|
|
138
|
+
return envNames[providerId] || '';
|
|
139
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.standardAcpBehavior = void 0;
|
|
4
|
+
exports.standardAcpBehavior = {
|
|
5
|
+
normalizeAssistantText(input) {
|
|
6
|
+
return input.rawText;
|
|
7
|
+
},
|
|
8
|
+
normalizeFinalAssistantText(input) {
|
|
9
|
+
return input.rawText;
|
|
10
|
+
},
|
|
11
|
+
};
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.createBuiltinAgentPlugin = createBuiltinAgentPlugin;
|
|
4
|
+
const desktop_js_1 = require("../../../../../shared/desktop.js");
|
|
5
|
+
const workspace_route_config_js_1 = require("../../router/workspace-route-config.js");
|
|
6
|
+
function createRuntime(agentType, match, displayName) {
|
|
7
|
+
return {
|
|
8
|
+
agentType,
|
|
9
|
+
transport: desktop_js_1.LOCALCORE_ACP_AGENT_TYPE,
|
|
10
|
+
displayName: displayName || agentType,
|
|
11
|
+
matchesProject(project) {
|
|
12
|
+
const normalizedAgentType = String(project.agent?.type || '').trim().toLowerCase();
|
|
13
|
+
return match(normalizedAgentType);
|
|
14
|
+
},
|
|
15
|
+
createRoute(configState, project) {
|
|
16
|
+
if (!this.matchesProject(project)) {
|
|
17
|
+
return null;
|
|
18
|
+
}
|
|
19
|
+
return {
|
|
20
|
+
kind: desktop_js_1.LOCALCORE_ACP_AGENT_TYPE,
|
|
21
|
+
agentType,
|
|
22
|
+
transport: desktop_js_1.LOCALCORE_ACP_AGENT_TYPE,
|
|
23
|
+
config: {
|
|
24
|
+
...(0, workspace_route_config_js_1.toLocalCoreProjectConfig)(configState, project),
|
|
25
|
+
agentType,
|
|
26
|
+
},
|
|
27
|
+
supportsStreamingProbe: true,
|
|
28
|
+
};
|
|
29
|
+
},
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
function createBuiltinAgentPlugin(options) {
|
|
33
|
+
const agentType = options.definition?.agentType || options.agentType || '';
|
|
34
|
+
const displayName = options.definition?.displayName || options.displayName || agentType;
|
|
35
|
+
const pluginId = options.pluginId || `builtin.agent-${agentType}`;
|
|
36
|
+
let runtime = null;
|
|
37
|
+
return {
|
|
38
|
+
manifest: {
|
|
39
|
+
id: pluginId,
|
|
40
|
+
kind: 'agent',
|
|
41
|
+
version: '0.1.0',
|
|
42
|
+
provides: [`agent:${agentType}`],
|
|
43
|
+
},
|
|
44
|
+
capabilities: {
|
|
45
|
+
agents: [
|
|
46
|
+
{
|
|
47
|
+
id: `agent.${agentType}`,
|
|
48
|
+
agentType,
|
|
49
|
+
displayName,
|
|
50
|
+
},
|
|
51
|
+
],
|
|
52
|
+
},
|
|
53
|
+
createRuntime(_ctx) {
|
|
54
|
+
if (!runtime) {
|
|
55
|
+
runtime = createRuntime(agentType, options.match, displayName);
|
|
56
|
+
}
|
|
57
|
+
return { runtime };
|
|
58
|
+
},
|
|
59
|
+
};
|
|
60
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.normalizeAgentType = normalizeAgentType;
|
|
4
|
+
exports.agentDefinitionMatches = agentDefinitionMatches;
|
|
5
|
+
function normalizeAgentType(value) {
|
|
6
|
+
return String(value || '').trim().toLowerCase();
|
|
7
|
+
}
|
|
8
|
+
function agentDefinitionMatches(definition, agentType) {
|
|
9
|
+
const normalized = normalizeAgentType(agentType);
|
|
10
|
+
return normalized === definition.agentType
|
|
11
|
+
|| Boolean(definition.aliases?.some((alias) => normalizeAgentType(alias) === normalized));
|
|
12
|
+
}
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getProviderDefaultModelId = getProviderDefaultModelId;
|
|
4
|
+
exports.getFirstProviderModelId = getFirstProviderModelId;
|
|
5
|
+
exports.collectProviderEnv = collectProviderEnv;
|
|
6
|
+
exports.normalizeProviderId = normalizeProviderId;
|
|
7
|
+
exports.splitProviderModelRef = splitProviderModelRef;
|
|
8
|
+
exports.ensurePrivateDir = ensurePrivateDir;
|
|
9
|
+
exports.writeJsonFile = writeJsonFile;
|
|
10
|
+
exports.projectLocalStateDir = projectLocalStateDir;
|
|
11
|
+
exports.resolveBundledAcpCommand = resolveBundledAcpCommand;
|
|
12
|
+
exports.resolveBundledPackageJsonPath = resolveBundledPackageJsonPath;
|
|
13
|
+
const node_module_1 = require("node:module");
|
|
14
|
+
const node_fs_1 = require("node:fs");
|
|
15
|
+
const node_path_1 = require("node:path");
|
|
16
|
+
function getProviderDefaultModelId(provider) {
|
|
17
|
+
const directModel = String(provider.model || '').trim();
|
|
18
|
+
if (directModel) {
|
|
19
|
+
return directModel;
|
|
20
|
+
}
|
|
21
|
+
const firstModel = Array.isArray(provider.models)
|
|
22
|
+
? provider.models.find((entry) => String(entry?.model || '').trim())
|
|
23
|
+
: null;
|
|
24
|
+
return String(firstModel?.model || '').trim();
|
|
25
|
+
}
|
|
26
|
+
function getFirstProviderModelId(providers) {
|
|
27
|
+
for (const provider of providers) {
|
|
28
|
+
const modelId = getProviderDefaultModelId(provider);
|
|
29
|
+
if (modelId) {
|
|
30
|
+
return modelId;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
return '';
|
|
34
|
+
}
|
|
35
|
+
function collectProviderEnv(providers) {
|
|
36
|
+
const env = {};
|
|
37
|
+
for (const provider of providers) {
|
|
38
|
+
if (!provider.env || typeof provider.env !== 'object') {
|
|
39
|
+
continue;
|
|
40
|
+
}
|
|
41
|
+
for (const [key, value] of Object.entries(provider.env)) {
|
|
42
|
+
const envKey = key.trim();
|
|
43
|
+
if (envKey) {
|
|
44
|
+
env[envKey] = String(value ?? '');
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
return env;
|
|
49
|
+
}
|
|
50
|
+
function normalizeProviderId(value) {
|
|
51
|
+
return String(value || '')
|
|
52
|
+
.trim()
|
|
53
|
+
.toLowerCase()
|
|
54
|
+
.replace(/[^a-z0-9]+/g, '-')
|
|
55
|
+
.replace(/^-+|-+$/g, '');
|
|
56
|
+
}
|
|
57
|
+
function splitProviderModelRef(value) {
|
|
58
|
+
const trimmed = value.trim();
|
|
59
|
+
const slashIndex = trimmed.indexOf('/');
|
|
60
|
+
if (slashIndex <= 0 || slashIndex >= trimmed.length - 1) {
|
|
61
|
+
return ['', trimmed];
|
|
62
|
+
}
|
|
63
|
+
return [trimmed.slice(0, slashIndex), trimmed.slice(slashIndex + 1)];
|
|
64
|
+
}
|
|
65
|
+
function ensurePrivateDir(path) {
|
|
66
|
+
(0, node_fs_1.mkdirSync)(path, { recursive: true, mode: 0o700 });
|
|
67
|
+
(0, node_fs_1.chmodSync)(path, 0o700);
|
|
68
|
+
}
|
|
69
|
+
function writeJsonFile(path, value, mode = 0o600) {
|
|
70
|
+
(0, node_fs_1.writeFileSync)(path, `${JSON.stringify(value, null, 2)}\n`, { encoding: 'utf8', mode });
|
|
71
|
+
(0, node_fs_1.chmodSync)(path, mode);
|
|
72
|
+
}
|
|
73
|
+
function projectLocalStateDir(configState, folderName, projectName) {
|
|
74
|
+
const configDir = (0, node_path_1.dirname)(configState.path);
|
|
75
|
+
const safeProjectName = String(projectName || 'workspace')
|
|
76
|
+
.trim()
|
|
77
|
+
.replace(/[^a-zA-Z0-9._-]+/g, '-')
|
|
78
|
+
.replace(/^-+|-+$/g, '') || 'workspace';
|
|
79
|
+
return (0, node_path_1.resolve)(configDir, folderName, safeProjectName);
|
|
80
|
+
}
|
|
81
|
+
function resolveBundledAcpCommand(packageName, binName) {
|
|
82
|
+
const require = (0, node_module_1.createRequire)(__filename);
|
|
83
|
+
const packageJsonPath = resolveBundledPackageJsonPath(packageName);
|
|
84
|
+
const packageJson = require(packageJsonPath);
|
|
85
|
+
const binField = packageJson.bin;
|
|
86
|
+
const relativeBinPath = typeof binField === 'string'
|
|
87
|
+
? binField
|
|
88
|
+
: binField?.[binName];
|
|
89
|
+
if (!relativeBinPath) {
|
|
90
|
+
throw new Error(`Bundled package "${packageName}" does not declare the ${binName} bin.`);
|
|
91
|
+
}
|
|
92
|
+
return {
|
|
93
|
+
command: process.execPath,
|
|
94
|
+
args: [(0, node_path_1.resolve)((0, node_path_1.dirname)(packageJsonPath), relativeBinPath)],
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
function resolveBundledPackageJsonPath(packageName) {
|
|
98
|
+
const require = (0, node_module_1.createRequire)(__filename);
|
|
99
|
+
try {
|
|
100
|
+
return require.resolve(`${packageName}/package.json`);
|
|
101
|
+
}
|
|
102
|
+
catch (error) {
|
|
103
|
+
if (error?.code !== 'ERR_PACKAGE_PATH_NOT_EXPORTED') {
|
|
104
|
+
throw error;
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
for (const basePath of require.resolve.paths(packageName) || []) {
|
|
108
|
+
const packageJsonPath = (0, node_path_1.resolve)(basePath, ...packageName.split('/'), 'package.json');
|
|
109
|
+
if ((0, node_fs_1.existsSync)(packageJsonPath)) {
|
|
110
|
+
return packageJsonPath;
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
let current = (0, node_path_1.dirname)(require.resolve(packageName));
|
|
114
|
+
while (current && current !== (0, node_path_1.dirname)(current)) {
|
|
115
|
+
const packageJsonPath = (0, node_path_1.resolve)(current, 'package.json');
|
|
116
|
+
if ((0, node_fs_1.existsSync)(packageJsonPath)) {
|
|
117
|
+
return packageJsonPath;
|
|
118
|
+
}
|
|
119
|
+
current = (0, node_path_1.dirname)(current);
|
|
120
|
+
}
|
|
121
|
+
throw new Error(`Bundled package "${packageName}" package.json could not be resolved.`);
|
|
122
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.hasPriorProgressMessage = hasPriorProgressMessage;
|
|
4
|
+
function hasPriorProgressMessage(input) {
|
|
5
|
+
const content = normalizeProgressContent(input.content);
|
|
6
|
+
if (!content) {
|
|
7
|
+
return false;
|
|
8
|
+
}
|
|
9
|
+
const kind = input.kind;
|
|
10
|
+
return input.priorProgressMessages.some((message) => {
|
|
11
|
+
if (kind && message.kind && message.kind !== kind) {
|
|
12
|
+
return false;
|
|
13
|
+
}
|
|
14
|
+
return normalizeProgressContent(message.content) === content;
|
|
15
|
+
});
|
|
16
|
+
}
|
|
17
|
+
function normalizeProgressContent(content) {
|
|
18
|
+
return String(content || '').replace(/\r\n/g, '\n').trim();
|
|
19
|
+
}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.stripAssistantReplayPrefix = stripAssistantReplayPrefix;
|
|
4
|
+
function stripAssistantReplayPrefix(rawText, priorAssistantMessages) {
|
|
5
|
+
const replayPrefix = priorAssistantMessages.join('');
|
|
6
|
+
if (!replayPrefix || !rawText) {
|
|
7
|
+
return rawText;
|
|
8
|
+
}
|
|
9
|
+
if (replayPrefix.startsWith(rawText)) {
|
|
10
|
+
return '';
|
|
11
|
+
}
|
|
12
|
+
if (priorAssistantMessages.some((message) => message.startsWith(rawText))) {
|
|
13
|
+
return '';
|
|
14
|
+
}
|
|
15
|
+
if (rawText.startsWith(replayPrefix)) {
|
|
16
|
+
return rawText.slice(replayPrefix.length);
|
|
17
|
+
}
|
|
18
|
+
const anchoredText = stripAfterLatestPriorMessageAnchor(rawText, priorAssistantMessages);
|
|
19
|
+
if (anchoredText !== null) {
|
|
20
|
+
return anchoredText;
|
|
21
|
+
}
|
|
22
|
+
const overlap = longestSuffixPrefixOverlap(replayPrefix, rawText);
|
|
23
|
+
if (overlap > 0 && overlap === rawText.length) {
|
|
24
|
+
return '';
|
|
25
|
+
}
|
|
26
|
+
return rawText;
|
|
27
|
+
}
|
|
28
|
+
function stripAfterLatestPriorMessageAnchor(rawText, priorAssistantMessages) {
|
|
29
|
+
let latestMatch = null;
|
|
30
|
+
for (const message of priorAssistantMessages) {
|
|
31
|
+
for (const anchor of createPriorMessageAnchors(message)) {
|
|
32
|
+
const index = rawText.lastIndexOf(anchor);
|
|
33
|
+
if (index < 0) {
|
|
34
|
+
continue;
|
|
35
|
+
}
|
|
36
|
+
const match = { index, length: anchor.length };
|
|
37
|
+
if (!latestMatch || match.index + match.length > latestMatch.index + latestMatch.length) {
|
|
38
|
+
latestMatch = match;
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
if (!latestMatch) {
|
|
43
|
+
return null;
|
|
44
|
+
}
|
|
45
|
+
return rawText.slice(latestMatch.index + latestMatch.length);
|
|
46
|
+
}
|
|
47
|
+
function createPriorMessageAnchors(message) {
|
|
48
|
+
const trimmed = message.trim();
|
|
49
|
+
if (trimmed.length < 32) {
|
|
50
|
+
return [];
|
|
51
|
+
}
|
|
52
|
+
const anchors = [];
|
|
53
|
+
for (const length of [240, 160, 96, 48, 32]) {
|
|
54
|
+
if (trimmed.length >= length) {
|
|
55
|
+
anchors.push(trimmed.slice(-length));
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
return anchors;
|
|
59
|
+
}
|
|
60
|
+
function longestSuffixPrefixOverlap(prefix, value) {
|
|
61
|
+
const max = Math.min(prefix.length, value.length);
|
|
62
|
+
for (let size = max; size > 0; size -= 1) {
|
|
63
|
+
if (prefix.endsWith(value.slice(0, size))) {
|
|
64
|
+
return size;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
return 0;
|
|
68
|
+
}
|
|
@@ -395,7 +395,6 @@ class LocalCoreLarkGateway extends node_events_1.EventEmitter {
|
|
|
395
395
|
const sessionKey = event.sessionKey;
|
|
396
396
|
const route = this.threadRouting.get(sessionKey);
|
|
397
397
|
if (!route) {
|
|
398
|
-
this.options.log?.(`localcore-lark bridge route miss for sessionKey=${sessionKey} type=${event.type}`);
|
|
399
398
|
return;
|
|
400
399
|
}
|
|
401
400
|
const routeInstanceId = route.instanceId || 'default';
|
|
@@ -481,7 +480,6 @@ class LocalCoreLarkGateway extends node_events_1.EventEmitter {
|
|
|
481
480
|
const shouldThrottle = event.type === 'update_message' &&
|
|
482
481
|
existingMessageId &&
|
|
483
482
|
Date.now() - (turn.lastPatchedAtByMessageId[existingMessageId] || 0) < (renderedMessage.isFinal ? LARK_FINAL_PATCH_INTERVAL_MS : LARK_PROGRESS_PATCH_INTERVAL_MS);
|
|
484
|
-
this.options.log?.(`localcore-lark bridge event type=${event.type} sessionKey=${sessionKey} hasMessageId=${Boolean(existingMessageId)} throttle=${shouldThrottle}`);
|
|
485
483
|
if (shouldThrottle) {
|
|
486
484
|
continue;
|
|
487
485
|
}
|
|
@@ -188,7 +188,7 @@ function takePendingLarkThoughtRender(turn) {
|
|
|
188
188
|
}
|
|
189
189
|
function getLarkRenderedMessageId(turn, rendered) {
|
|
190
190
|
if (rendered.isFinal) {
|
|
191
|
-
return
|
|
191
|
+
return undefined;
|
|
192
192
|
}
|
|
193
193
|
return turn.progressMessageIds[rendered.key];
|
|
194
194
|
}
|