@corbat-tech/coco 2.28.0 → 2.28.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli/index.js +63 -14
- package/dist/cli/index.js.map +1 -1
- package/dist/index.js +9 -2
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/cli/index.js
CHANGED
|
@@ -29710,8 +29710,7 @@ var PROVIDER_DEFINITIONS = {
|
|
|
29710
29710
|
name: "Gemini 3 Pro (Preview)",
|
|
29711
29711
|
description: "Most capable Vertex Gemini 3 model (preview)",
|
|
29712
29712
|
contextWindow: 1048576,
|
|
29713
|
-
maxOutputTokens: 65536
|
|
29714
|
-
recommended: true
|
|
29713
|
+
maxOutputTokens: 65536
|
|
29715
29714
|
},
|
|
29716
29715
|
{
|
|
29717
29716
|
id: "gemini-3-flash-preview",
|
|
@@ -29725,7 +29724,8 @@ var PROVIDER_DEFINITIONS = {
|
|
|
29725
29724
|
name: "Gemini 2.5 Pro",
|
|
29726
29725
|
description: "Stable high-quality Vertex model for coding and complex reasoning",
|
|
29727
29726
|
contextWindow: 1048576,
|
|
29728
|
-
maxOutputTokens: 65536
|
|
29727
|
+
maxOutputTokens: 65536,
|
|
29728
|
+
recommended: true
|
|
29729
29729
|
},
|
|
29730
29730
|
{
|
|
29731
29731
|
id: "gemini-2.5-flash",
|
|
@@ -35948,7 +35948,7 @@ Using existing API key...`));
|
|
|
35948
35948
|
}
|
|
35949
35949
|
const rememberedModel = await getLastUsedModel(newProvider.id);
|
|
35950
35950
|
const recommendedModel = getRecommendedModel(newProvider.id);
|
|
35951
|
-
|
|
35951
|
+
let newModel = rememberedModel || recommendedModel?.id || newProvider.models[0]?.id || "";
|
|
35952
35952
|
const resolvedVertexProject = newProvider.id === "vertex" ? (vertexSettings?.project ?? session.config.provider.project ?? process.env["VERTEX_PROJECT"] ?? process.env["GOOGLE_CLOUD_PROJECT"] ?? process.env["GCLOUD_PROJECT"] ?? "").trim() : void 0;
|
|
35953
35953
|
const resolvedVertexLocation = newProvider.id === "vertex" ? (vertexSettings?.location ?? session.config.provider.location ?? process.env["VERTEX_LOCATION"] ?? process.env["GOOGLE_CLOUD_LOCATION"] ?? "global").trim() : void 0;
|
|
35954
35954
|
const spinner18 = p26.spinner();
|
|
@@ -35959,7 +35959,31 @@ Using existing API key...`));
|
|
|
35959
35959
|
project: resolvedVertexProject,
|
|
35960
35960
|
location: resolvedVertexLocation
|
|
35961
35961
|
});
|
|
35962
|
-
|
|
35962
|
+
let available = await testProvider.isAvailable();
|
|
35963
|
+
if (!available && newProvider.id === "vertex") {
|
|
35964
|
+
const fallbackModels = ["gemini-2.5-pro", "gemini-2.5-flash", "gemini-2.0-flash-001"].filter(
|
|
35965
|
+
(modelId) => modelId !== newModel
|
|
35966
|
+
);
|
|
35967
|
+
for (const fallbackModel of fallbackModels) {
|
|
35968
|
+
const fallbackProvider = await createProvider(internalProviderId, {
|
|
35969
|
+
model: fallbackModel,
|
|
35970
|
+
project: resolvedVertexProject,
|
|
35971
|
+
location: resolvedVertexLocation
|
|
35972
|
+
});
|
|
35973
|
+
const fallbackAvailable = await fallbackProvider.isAvailable();
|
|
35974
|
+
if (fallbackAvailable) {
|
|
35975
|
+
newModel = fallbackModel;
|
|
35976
|
+
available = true;
|
|
35977
|
+
console.log(
|
|
35978
|
+
chalk.yellow(
|
|
35979
|
+
`
|
|
35980
|
+
\u26A0\uFE0F The selected Vertex model was not available. Using fallback model: ${fallbackModel}`
|
|
35981
|
+
)
|
|
35982
|
+
);
|
|
35983
|
+
break;
|
|
35984
|
+
}
|
|
35985
|
+
}
|
|
35986
|
+
}
|
|
35963
35987
|
if (!available) {
|
|
35964
35988
|
spinner18.stop(chalk.red("Connection failed"));
|
|
35965
35989
|
console.log(chalk.red(`
|
|
@@ -44935,6 +44959,11 @@ var DEFAULT_SEARCH_TIMEOUT_MS = 15e3;
|
|
|
44935
44959
|
var MAX_QUERY_LENGTH = 500;
|
|
44936
44960
|
var MIN_REQUEST_INTERVAL_MS = 1e3;
|
|
44937
44961
|
var lastRequestTime = 0;
|
|
44962
|
+
function isEngineConfigured(engine) {
|
|
44963
|
+
if (engine === "duckduckgo") return true;
|
|
44964
|
+
if (engine === "brave") return !!process.env.BRAVE_SEARCH_API_KEY;
|
|
44965
|
+
return !!process.env.SERPAPI_KEY;
|
|
44966
|
+
}
|
|
44938
44967
|
function sanitizeQuery(query) {
|
|
44939
44968
|
const cleaned = query.replace(/[\x00-\x1F\x7F]/g, " ").trim();
|
|
44940
44969
|
return cleaned.slice(0, MAX_QUERY_LENGTH);
|
|
@@ -45136,7 +45165,9 @@ Examples:
|
|
|
45136
45165
|
await enforceRateLimit();
|
|
45137
45166
|
try {
|
|
45138
45167
|
let results;
|
|
45139
|
-
|
|
45168
|
+
const requestedEngine = engine;
|
|
45169
|
+
const effectiveEngine = isEngineConfigured(requestedEngine) ? requestedEngine : "duckduckgo";
|
|
45170
|
+
switch (effectiveEngine) {
|
|
45140
45171
|
case "brave":
|
|
45141
45172
|
results = await searchBrave(sanitizedQuery, maxResults, DEFAULT_SEARCH_TIMEOUT_MS);
|
|
45142
45173
|
break;
|
|
@@ -45151,7 +45182,7 @@ Examples:
|
|
|
45151
45182
|
return {
|
|
45152
45183
|
results,
|
|
45153
45184
|
totalResults: results.length,
|
|
45154
|
-
engine:
|
|
45185
|
+
engine: effectiveEngine,
|
|
45155
45186
|
duration: performance.now() - startTime
|
|
45156
45187
|
};
|
|
45157
45188
|
} catch (error) {
|
|
@@ -53296,6 +53327,30 @@ async function executeAgentTurn(session, userMessage, provider, toolRegistry, op
|
|
|
53296
53327
|
[... ${omitted.toLocaleString()} characters omitted \u2014 use read_file with offset/limit to retrieve more of '${toolName}' output ...]
|
|
53297
53328
|
${tail}`;
|
|
53298
53329
|
}
|
|
53330
|
+
function stableSerialize(value) {
|
|
53331
|
+
if (value === null || typeof value !== "object") {
|
|
53332
|
+
try {
|
|
53333
|
+
return JSON.stringify(value);
|
|
53334
|
+
} catch {
|
|
53335
|
+
return "null";
|
|
53336
|
+
}
|
|
53337
|
+
}
|
|
53338
|
+
if (Array.isArray(value)) {
|
|
53339
|
+
return `[${value.map((item) => stableSerialize(item)).join(",")}]`;
|
|
53340
|
+
}
|
|
53341
|
+
const objectValue = value;
|
|
53342
|
+
const keys = Object.keys(objectValue).sort();
|
|
53343
|
+
return `{${keys.map((key) => `${JSON.stringify(key)}:${stableSerialize(objectValue[key])}`).join(",")}}`;
|
|
53344
|
+
}
|
|
53345
|
+
function getToolCallDedupeFingerprint(toolCall) {
|
|
53346
|
+
if (toolCall.name === "bash_exec") {
|
|
53347
|
+
const input = toolCall.input ?? {};
|
|
53348
|
+
const command = String(input.command ?? "").replace(/\s+/g, " ").trim();
|
|
53349
|
+
const cwd = String(input.cwd ?? "").replace(/\s+/g, " ").trim();
|
|
53350
|
+
return `bash_exec:${command}:cwd=${cwd}`;
|
|
53351
|
+
}
|
|
53352
|
+
return `${toolCall.name}:${stableSerialize(toolCall.input ?? {})}`;
|
|
53353
|
+
}
|
|
53299
53354
|
function shouldRecoverNoToolTurn(stopReason, content) {
|
|
53300
53355
|
const trimmed = content.trim();
|
|
53301
53356
|
if (stopReason === "tool_use") {
|
|
@@ -53497,13 +53552,7 @@ ${tail}`;
|
|
|
53497
53552
|
const dedupedToolCalls = [];
|
|
53498
53553
|
const seenToolCallFingerprints = /* @__PURE__ */ new Set();
|
|
53499
53554
|
for (const toolCall of collectedToolCalls) {
|
|
53500
|
-
|
|
53501
|
-
try {
|
|
53502
|
-
inputSerialized = JSON.stringify(toolCall.input ?? {});
|
|
53503
|
-
} catch {
|
|
53504
|
-
inputSerialized = "{}";
|
|
53505
|
-
}
|
|
53506
|
-
const fingerprint = `${toolCall.name}:${inputSerialized}`;
|
|
53555
|
+
const fingerprint = getToolCallDedupeFingerprint(toolCall);
|
|
53507
53556
|
if (seenToolCallFingerprints.has(fingerprint)) {
|
|
53508
53557
|
continue;
|
|
53509
53558
|
}
|