@probelabs/probe 0.6.0-rc161 → 0.6.0-rc163

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/cjs/index.cjs CHANGED
@@ -11223,7 +11223,10 @@ var init_CborCodec = __esm({
11223
11223
  }
11224
11224
  } else if (ns.isStructSchema()) {
11225
11225
  for (const [key, memberSchema] of ns.structIterator()) {
11226
- newObject[key] = this.readValue(memberSchema, value[key]);
11226
+ const v3 = this.readValue(memberSchema, value[key]);
11227
+ if (v3 != null) {
11228
+ newObject[key] = v3;
11229
+ }
11227
11230
  }
11228
11231
  }
11229
11232
  return newObject;
@@ -12744,10 +12747,7 @@ var init_JsonShapeSerializer = __esm({
12744
12747
  if (ns === this.rootSchema) {
12745
12748
  return value;
12746
12749
  }
12747
- if (!this.serdeContext?.base64Encoder) {
12748
- return (0, import_util_base645.toBase64)(value);
12749
- }
12750
- return this.serdeContext?.base64Encoder(value);
12750
+ return (this.serdeContext?.base64Encoder ?? import_util_base645.toBase64)(value);
12751
12751
  }
12752
12752
  if ((ns.isTimestampSchema() || ns.isDocumentSchema()) && value instanceof Date) {
12753
12753
  const format2 = determineTimestampFormat(ns, this.settings);
@@ -14382,7 +14382,13 @@ var init_AwsQueryProtocol = __esm({
14382
14382
  Code: errorData.Code,
14383
14383
  Message: message
14384
14384
  };
14385
- const { errorSchema, errorMetadata } = await this.mixin.getErrorSchemaOrThrowBaseException(errorIdentifier, this.options.defaultNamespace, response, errorData, metadata, (registry, errorName) => registry.find((schema) => NormalizedSchema.of(schema).getMergedTraits().awsQueryError?.[0] === errorName));
14385
+ const { errorSchema, errorMetadata } = await this.mixin.getErrorSchemaOrThrowBaseException(errorIdentifier, this.options.defaultNamespace, response, errorData, metadata, (registry, errorName) => {
14386
+ try {
14387
+ return registry.getSchema(errorName);
14388
+ } catch (e3) {
14389
+ return registry.find((schema) => NormalizedSchema.of(schema).getMergedTraits().awsQueryError?.[0] === errorName);
14390
+ }
14391
+ });
14386
14392
  const ns = NormalizedSchema.of(errorSchema);
14387
14393
  const ErrorCtor = TypeRegistry.for(errorSchema[1]).getErrorCtor(errorSchema) ?? Error;
14388
14394
  const exception = new ErrorCtor(message);
@@ -16748,7 +16754,11 @@ var require_dist_cjs39 = __commonJS({
16748
16754
  var validRegions = /* @__PURE__ */ new Set();
16749
16755
  var checkRegion = (region, check = utilEndpoints.isValidHostLabel) => {
16750
16756
  if (!validRegions.has(region) && !check(region)) {
16751
- throw new Error(`Region not accepted: region="${region}" is not a valid hostname component.`);
16757
+ if (region === "*") {
16758
+ console.warn(`@smithy/config-resolver WARN - Please use the caller region instead of "*". See "sigv4a" in https://github.com/aws/aws-sdk-js-v3/blob/main/supplemental-docs/CLIENTS.md.`);
16759
+ } else {
16760
+ throw new Error(`Region not accepted: region="${region}" is not a valid hostname component.`);
16761
+ }
16752
16762
  } else {
16753
16763
  validRegions.add(region);
16754
16764
  }
@@ -16946,42 +16956,40 @@ var require_getSSOTokenFromFile = __commonJS({
16946
16956
  "use strict";
16947
16957
  Object.defineProperty(exports2, "__esModule", { value: true });
16948
16958
  exports2.getSSOTokenFromFile = exports2.tokenIntercept = void 0;
16949
- var fs_1 = require("fs");
16959
+ var promises_1 = require("fs/promises");
16950
16960
  var getSSOTokenFilepath_1 = require_getSSOTokenFilepath();
16951
- var { readFile: readFile2 } = fs_1.promises;
16952
16961
  exports2.tokenIntercept = {};
16953
16962
  var getSSOTokenFromFile = async (id) => {
16954
16963
  if (exports2.tokenIntercept[id]) {
16955
16964
  return exports2.tokenIntercept[id];
16956
16965
  }
16957
16966
  const ssoTokenFilepath = (0, getSSOTokenFilepath_1.getSSOTokenFilepath)(id);
16958
- const ssoTokenText = await readFile2(ssoTokenFilepath, "utf8");
16967
+ const ssoTokenText = await (0, promises_1.readFile)(ssoTokenFilepath, "utf8");
16959
16968
  return JSON.parse(ssoTokenText);
16960
16969
  };
16961
16970
  exports2.getSSOTokenFromFile = getSSOTokenFromFile;
16962
16971
  }
16963
16972
  });
16964
16973
 
16965
- // node_modules/@smithy/shared-ini-file-loader/dist-cjs/slurpFile.js
16966
- var require_slurpFile = __commonJS({
16967
- "node_modules/@smithy/shared-ini-file-loader/dist-cjs/slurpFile.js"(exports2) {
16974
+ // node_modules/@smithy/shared-ini-file-loader/dist-cjs/readFile.js
16975
+ var require_readFile = __commonJS({
16976
+ "node_modules/@smithy/shared-ini-file-loader/dist-cjs/readFile.js"(exports2) {
16968
16977
  "use strict";
16969
16978
  Object.defineProperty(exports2, "__esModule", { value: true });
16970
- exports2.slurpFile = exports2.fileIntercept = exports2.filePromisesHash = void 0;
16971
- var fs_1 = require("fs");
16972
- var { readFile: readFile2 } = fs_1.promises;
16973
- exports2.filePromisesHash = {};
16979
+ exports2.readFile = exports2.fileIntercept = exports2.filePromises = void 0;
16980
+ var promises_1 = require("node:fs/promises");
16981
+ exports2.filePromises = {};
16974
16982
  exports2.fileIntercept = {};
16975
- var slurpFile = (path7, options) => {
16983
+ var readFile2 = (path7, options) => {
16976
16984
  if (exports2.fileIntercept[path7] !== void 0) {
16977
16985
  return exports2.fileIntercept[path7];
16978
16986
  }
16979
- if (!exports2.filePromisesHash[path7] || options?.ignoreCache) {
16980
- exports2.filePromisesHash[path7] = readFile2(path7, "utf8");
16987
+ if (!exports2.filePromises[path7] || options?.ignoreCache) {
16988
+ exports2.filePromises[path7] = (0, promises_1.readFile)(path7, "utf8");
16981
16989
  }
16982
- return exports2.filePromisesHash[path7];
16990
+ return exports2.filePromises[path7];
16983
16991
  };
16984
- exports2.slurpFile = slurpFile;
16992
+ exports2.readFile = readFile2;
16985
16993
  }
16986
16994
  });
16987
16995
 
@@ -16994,7 +17002,7 @@ var require_dist_cjs42 = __commonJS({
16994
17002
  var getSSOTokenFromFile = require_getSSOTokenFromFile();
16995
17003
  var path7 = require("path");
16996
17004
  var types2 = require_dist_cjs();
16997
- var slurpFile = require_slurpFile();
17005
+ var readFile2 = require_readFile();
16998
17006
  var ENV_PROFILE = "AWS_PROFILE";
16999
17007
  var DEFAULT_PROFILE = "default";
17000
17008
  var getProfileName = (init) => init.profile || process.env[ENV_PROFILE] || DEFAULT_PROFILE;
@@ -17078,10 +17086,10 @@ var require_dist_cjs42 = __commonJS({
17078
17086
  resolvedConfigFilepath = path7.join(homeDir, configFilepath.slice(2));
17079
17087
  }
17080
17088
  const parsedFiles = await Promise.all([
17081
- slurpFile.slurpFile(resolvedConfigFilepath, {
17089
+ readFile2.readFile(resolvedConfigFilepath, {
17082
17090
  ignoreCache: init.ignoreCache
17083
17091
  }).then(parseIni).then(getConfigData).catch(swallowError$1),
17084
- slurpFile.slurpFile(resolvedFilepath, {
17092
+ readFile2.readFile(resolvedFilepath, {
17085
17093
  ignoreCache: init.ignoreCache
17086
17094
  }).then(parseIni).catch(swallowError$1)
17087
17095
  ]);
@@ -17092,7 +17100,7 @@ var require_dist_cjs42 = __commonJS({
17092
17100
  };
17093
17101
  var getSsoSessionData = (data2) => Object.entries(data2).filter(([key]) => key.startsWith(types2.IniSectionType.SSO_SESSION + CONFIG_PREFIX_SEPARATOR)).reduce((acc, [key, value]) => ({ ...acc, [key.substring(key.indexOf(CONFIG_PREFIX_SEPARATOR) + 1)]: value }), {});
17094
17102
  var swallowError = () => ({});
17095
- var loadSsoSessionData = async (init = {}) => slurpFile.slurpFile(init.configFilepath ?? getConfigFilepath()).then(parseIni).then(getSsoSessionData).catch(swallowError);
17103
+ var loadSsoSessionData = async (init = {}) => readFile2.readFile(init.configFilepath ?? getConfigFilepath()).then(parseIni).then(getSsoSessionData).catch(swallowError);
17096
17104
  var mergeConfigFiles = (...files) => {
17097
17105
  const merged = {};
17098
17106
  for (const file of files) {
@@ -17112,10 +17120,10 @@ var require_dist_cjs42 = __commonJS({
17112
17120
  };
17113
17121
  var externalDataInterceptor = {
17114
17122
  getFileRecord() {
17115
- return slurpFile.fileIntercept;
17123
+ return readFile2.fileIntercept;
17116
17124
  },
17117
17125
  interceptFile(path8, contents) {
17118
- slurpFile.fileIntercept[path8] = Promise.resolve(contents);
17126
+ readFile2.fileIntercept[path8] = Promise.resolve(contents);
17119
17127
  },
17120
17128
  getTokenRecord() {
17121
17129
  return getSSOTokenFromFile.tokenIntercept;
@@ -17130,6 +17138,12 @@ var require_dist_cjs42 = __commonJS({
17130
17138
  return getSSOTokenFromFile.getSSOTokenFromFile;
17131
17139
  }
17132
17140
  });
17141
+ Object.defineProperty(exports2, "readFile", {
17142
+ enumerable: true,
17143
+ get: function() {
17144
+ return readFile2.readFile;
17145
+ }
17146
+ });
17133
17147
  exports2.CONFIG_PREFIX_SEPARATOR = CONFIG_PREFIX_SEPARATOR;
17134
17148
  exports2.DEFAULT_PROFILE = DEFAULT_PROFILE;
17135
17149
  exports2.ENV_PROFILE = ENV_PROFILE;
@@ -18269,7 +18283,7 @@ var require_package2 = __commonJS({
18269
18283
  module2.exports = {
18270
18284
  name: "@aws-sdk/client-bedrock-runtime",
18271
18285
  description: "AWS SDK for JavaScript Bedrock Runtime Client for Node.js, Browser and React Native",
18272
- version: "3.922.0",
18286
+ version: "3.928.0",
18273
18287
  scripts: {
18274
18288
  build: "concurrently 'yarn:build:cjs' 'yarn:build:es' 'yarn:build:types'",
18275
18289
  "build:cjs": "node ../../scripts/compilation/inline client-bedrock-runtime",
@@ -18288,22 +18302,22 @@ var require_package2 = __commonJS({
18288
18302
  dependencies: {
18289
18303
  "@aws-crypto/sha256-browser": "5.2.0",
18290
18304
  "@aws-crypto/sha256-js": "5.2.0",
18291
- "@aws-sdk/core": "3.922.0",
18292
- "@aws-sdk/credential-provider-node": "3.922.0",
18305
+ "@aws-sdk/core": "3.928.0",
18306
+ "@aws-sdk/credential-provider-node": "3.928.0",
18293
18307
  "@aws-sdk/eventstream-handler-node": "3.922.0",
18294
18308
  "@aws-sdk/middleware-eventstream": "3.922.0",
18295
18309
  "@aws-sdk/middleware-host-header": "3.922.0",
18296
18310
  "@aws-sdk/middleware-logger": "3.922.0",
18297
18311
  "@aws-sdk/middleware-recursion-detection": "3.922.0",
18298
- "@aws-sdk/middleware-user-agent": "3.922.0",
18312
+ "@aws-sdk/middleware-user-agent": "3.928.0",
18299
18313
  "@aws-sdk/middleware-websocket": "3.922.0",
18300
- "@aws-sdk/region-config-resolver": "3.922.0",
18301
- "@aws-sdk/token-providers": "3.922.0",
18314
+ "@aws-sdk/region-config-resolver": "3.925.0",
18315
+ "@aws-sdk/token-providers": "3.928.0",
18302
18316
  "@aws-sdk/types": "3.922.0",
18303
18317
  "@aws-sdk/util-endpoints": "3.922.0",
18304
18318
  "@aws-sdk/util-user-agent-browser": "3.922.0",
18305
- "@aws-sdk/util-user-agent-node": "3.922.0",
18306
- "@smithy/config-resolver": "^4.4.1",
18319
+ "@aws-sdk/util-user-agent-node": "3.928.0",
18320
+ "@smithy/config-resolver": "^4.4.2",
18307
18321
  "@smithy/core": "^3.17.2",
18308
18322
  "@smithy/eventstream-serde-browser": "^4.2.4",
18309
18323
  "@smithy/eventstream-serde-config-resolver": "^4.3.4",
@@ -18326,7 +18340,7 @@ var require_package2 = __commonJS({
18326
18340
  "@smithy/util-body-length-browser": "^4.2.0",
18327
18341
  "@smithy/util-body-length-node": "^4.2.1",
18328
18342
  "@smithy/util-defaults-mode-browser": "^4.3.5",
18329
- "@smithy/util-defaults-mode-node": "^4.2.7",
18343
+ "@smithy/util-defaults-mode-node": "^4.2.8",
18330
18344
  "@smithy/util-endpoints": "^3.2.4",
18331
18345
  "@smithy/util-middleware": "^4.2.4",
18332
18346
  "@smithy/util-retry": "^4.2.4",
@@ -19050,7 +19064,7 @@ var init_package = __esm({
19050
19064
  "node_modules/@aws-sdk/nested-clients/package.json"() {
19051
19065
  package_default = {
19052
19066
  name: "@aws-sdk/nested-clients",
19053
- version: "3.922.0",
19067
+ version: "3.928.0",
19054
19068
  description: "Nested clients for AWS SDK packages.",
19055
19069
  main: "./dist-cjs/index.js",
19056
19070
  module: "./dist-es/index.js",
@@ -19079,17 +19093,17 @@ var init_package = __esm({
19079
19093
  dependencies: {
19080
19094
  "@aws-crypto/sha256-browser": "5.2.0",
19081
19095
  "@aws-crypto/sha256-js": "5.2.0",
19082
- "@aws-sdk/core": "3.922.0",
19096
+ "@aws-sdk/core": "3.928.0",
19083
19097
  "@aws-sdk/middleware-host-header": "3.922.0",
19084
19098
  "@aws-sdk/middleware-logger": "3.922.0",
19085
19099
  "@aws-sdk/middleware-recursion-detection": "3.922.0",
19086
- "@aws-sdk/middleware-user-agent": "3.922.0",
19087
- "@aws-sdk/region-config-resolver": "3.922.0",
19100
+ "@aws-sdk/middleware-user-agent": "3.928.0",
19101
+ "@aws-sdk/region-config-resolver": "3.925.0",
19088
19102
  "@aws-sdk/types": "3.922.0",
19089
19103
  "@aws-sdk/util-endpoints": "3.922.0",
19090
19104
  "@aws-sdk/util-user-agent-browser": "3.922.0",
19091
- "@aws-sdk/util-user-agent-node": "3.922.0",
19092
- "@smithy/config-resolver": "^4.4.1",
19105
+ "@aws-sdk/util-user-agent-node": "3.928.0",
19106
+ "@smithy/config-resolver": "^4.4.2",
19093
19107
  "@smithy/core": "^3.17.2",
19094
19108
  "@smithy/fetch-http-handler": "^5.3.5",
19095
19109
  "@smithy/hash-node": "^4.2.4",
@@ -19109,7 +19123,7 @@ var init_package = __esm({
19109
19123
  "@smithy/util-body-length-browser": "^4.2.0",
19110
19124
  "@smithy/util-body-length-node": "^4.2.1",
19111
19125
  "@smithy/util-defaults-mode-browser": "^4.3.5",
19112
- "@smithy/util-defaults-mode-node": "^4.2.7",
19126
+ "@smithy/util-defaults-mode-node": "^4.2.8",
19113
19127
  "@smithy/util-endpoints": "^3.2.4",
19114
19128
  "@smithy/util-middleware": "^4.2.4",
19115
19129
  "@smithy/util-retry": "^4.2.4",
@@ -20530,7 +20544,7 @@ var require_package3 = __commonJS({
20530
20544
  module2.exports = {
20531
20545
  name: "@aws-sdk/client-sso",
20532
20546
  description: "AWS SDK for JavaScript Sso Client for Node.js, Browser and React Native",
20533
- version: "3.922.0",
20547
+ version: "3.928.0",
20534
20548
  scripts: {
20535
20549
  build: "concurrently 'yarn:build:cjs' 'yarn:build:es' 'yarn:build:types'",
20536
20550
  "build:cjs": "node ../../scripts/compilation/inline client-sso",
@@ -20549,17 +20563,17 @@ var require_package3 = __commonJS({
20549
20563
  dependencies: {
20550
20564
  "@aws-crypto/sha256-browser": "5.2.0",
20551
20565
  "@aws-crypto/sha256-js": "5.2.0",
20552
- "@aws-sdk/core": "3.922.0",
20566
+ "@aws-sdk/core": "3.928.0",
20553
20567
  "@aws-sdk/middleware-host-header": "3.922.0",
20554
20568
  "@aws-sdk/middleware-logger": "3.922.0",
20555
20569
  "@aws-sdk/middleware-recursion-detection": "3.922.0",
20556
- "@aws-sdk/middleware-user-agent": "3.922.0",
20557
- "@aws-sdk/region-config-resolver": "3.922.0",
20570
+ "@aws-sdk/middleware-user-agent": "3.928.0",
20571
+ "@aws-sdk/region-config-resolver": "3.925.0",
20558
20572
  "@aws-sdk/types": "3.922.0",
20559
20573
  "@aws-sdk/util-endpoints": "3.922.0",
20560
20574
  "@aws-sdk/util-user-agent-browser": "3.922.0",
20561
- "@aws-sdk/util-user-agent-node": "3.922.0",
20562
- "@smithy/config-resolver": "^4.4.1",
20575
+ "@aws-sdk/util-user-agent-node": "3.928.0",
20576
+ "@smithy/config-resolver": "^4.4.2",
20563
20577
  "@smithy/core": "^3.17.2",
20564
20578
  "@smithy/fetch-http-handler": "^5.3.5",
20565
20579
  "@smithy/hash-node": "^4.2.4",
@@ -20579,7 +20593,7 @@ var require_package3 = __commonJS({
20579
20593
  "@smithy/util-body-length-browser": "^4.2.0",
20580
20594
  "@smithy/util-body-length-node": "^4.2.1",
20581
20595
  "@smithy/util-defaults-mode-browser": "^4.3.5",
20582
- "@smithy/util-defaults-mode-node": "^4.2.7",
20596
+ "@smithy/util-defaults-mode-node": "^4.2.8",
20583
20597
  "@smithy/util-endpoints": "^3.2.4",
20584
20598
  "@smithy/util-middleware": "^4.2.4",
20585
20599
  "@smithy/util-retry": "^4.2.4",
@@ -27873,6 +27887,162 @@ var init_BytePairEncodingCore = __esm({
27873
27887
  }
27874
27888
  });
27875
27889
 
27890
+ // node_modules/gpt-tokenizer/esm/functionCalling.js
27891
+ function countMessageTokens(message, countStringTokens) {
27892
+ let tokens = 0;
27893
+ if (message.role) {
27894
+ tokens += countStringTokens(message.role);
27895
+ }
27896
+ if (message.content) {
27897
+ tokens += countStringTokens(message.content);
27898
+ }
27899
+ if (message.name) {
27900
+ tokens += countStringTokens(message.name) + MESSAGE_NAME_TOKEN_OVERHEAD;
27901
+ }
27902
+ if (message.function_call) {
27903
+ const { name: name14, arguments: args } = message.function_call;
27904
+ if (name14) {
27905
+ tokens += countStringTokens(name14);
27906
+ }
27907
+ if (args) {
27908
+ tokens += countStringTokens(args);
27909
+ }
27910
+ tokens += FUNCTION_CALL_METADATA_TOKEN_OVERHEAD;
27911
+ }
27912
+ tokens += MESSAGE_TOKEN_OVERHEAD;
27913
+ if (message.role === "function") {
27914
+ tokens -= FUNCTION_ROLE_TOKEN_DISCOUNT;
27915
+ }
27916
+ return tokens;
27917
+ }
27918
+ function formatObjectProperties(obj, indent, formatType) {
27919
+ if (!obj.properties) {
27920
+ return "";
27921
+ }
27922
+ const lines = [];
27923
+ const requiredParams = new Set(obj.required ?? []);
27924
+ const indentString = " ".repeat(indent);
27925
+ for (const [name14, param] of Object.entries(obj.properties)) {
27926
+ if (param.description && indent < 2) {
27927
+ lines.push(`${indentString}// ${param.description}`);
27928
+ }
27929
+ const isRequired = requiredParams.has(name14);
27930
+ const formattedType = formatType(param, indent);
27931
+ lines.push(`${indentString}${name14}${isRequired ? "" : "?"}: ${formattedType},`);
27932
+ }
27933
+ return lines.join("\n");
27934
+ }
27935
+ function formatFunctionType(param, indent) {
27936
+ switch (param.type) {
27937
+ case "string":
27938
+ return param.enum?.map((value) => JSON.stringify(value)).join(" | ") ?? "string";
27939
+ case "integer":
27940
+ case "number":
27941
+ return param.enum?.map((value) => `${value}`).join(" | ") ?? "number";
27942
+ case "boolean":
27943
+ return "boolean";
27944
+ case "null":
27945
+ return "null";
27946
+ case "array":
27947
+ return param.items ? `${formatFunctionType(param.items, indent)}[]` : "any[]";
27948
+ case "object": {
27949
+ const inner = formatObjectProperties(param, indent + 2, formatFunctionType);
27950
+ const closingIndent = " ".repeat(indent);
27951
+ return `{
27952
+ ${inner}
27953
+ ${closingIndent}}`;
27954
+ }
27955
+ default:
27956
+ return "any";
27957
+ }
27958
+ }
27959
+ function formatFunctionDefinitions(functions) {
27960
+ const lines = ["namespace functions {", ""];
27961
+ for (const fn of functions) {
27962
+ if (fn.description) {
27963
+ lines.push(`// ${fn.description}`);
27964
+ }
27965
+ const { parameters } = fn;
27966
+ const properties = parameters?.properties;
27967
+ if (!parameters || !properties || Object.keys(properties).length === 0) {
27968
+ lines.push(`type ${fn.name} = () => any;`);
27969
+ } else {
27970
+ lines.push(`type ${fn.name} = (_: {`);
27971
+ const formattedProperties = formatObjectProperties(parameters, 0, formatFunctionType);
27972
+ if (formattedProperties.length > 0) {
27973
+ lines.push(formattedProperties);
27974
+ }
27975
+ lines.push("}) => any;");
27976
+ }
27977
+ lines.push("");
27978
+ }
27979
+ lines.push("} // namespace functions");
27980
+ return lines.join("\n");
27981
+ }
27982
+ function estimateTokensInFunctions(functions, countStringTokens) {
27983
+ const formatted = formatFunctionDefinitions(functions);
27984
+ let tokens = countStringTokens(formatted);
27985
+ tokens += FUNCTION_DEFINITION_TOKEN_OVERHEAD;
27986
+ return tokens;
27987
+ }
27988
+ function padSystemMessage(message, hasFunctions, isSystemPadded) {
27989
+ if (!hasFunctions || isSystemPadded || message.role !== "system") {
27990
+ return message;
27991
+ }
27992
+ if (!message.content || message.content.endsWith(NEWLINE)) {
27993
+ return message;
27994
+ }
27995
+ return {
27996
+ ...message,
27997
+ content: `${message.content}${NEWLINE}`
27998
+ };
27999
+ }
28000
+ function computeChatCompletionTokenCount(request, countStringTokens) {
28001
+ const { messages, functions, function_call: functionCall } = request;
28002
+ const hasFunctions = Boolean(functions && functions.length > 0);
28003
+ let paddedSystem = false;
28004
+ let total = 0;
28005
+ for (const message of messages) {
28006
+ const messageToCount = padSystemMessage(message, hasFunctions, paddedSystem);
28007
+ if (messageToCount !== message && message.role === "system") {
28008
+ paddedSystem = true;
28009
+ } else if (message.role === "system" && hasFunctions && !paddedSystem) {
28010
+ paddedSystem = true;
28011
+ }
28012
+ total += countMessageTokens(messageToCount, countStringTokens);
28013
+ }
28014
+ total += COMPLETION_REQUEST_TOKEN_OVERHEAD;
28015
+ if (hasFunctions && functions) {
28016
+ total += estimateTokensInFunctions(functions, countStringTokens);
28017
+ if (messages.some((message) => message.role === "system")) {
28018
+ total -= SYSTEM_FUNCTION_TOKEN_DEDUCTION;
28019
+ }
28020
+ }
28021
+ if (functionCall && functionCall !== "auto") {
28022
+ if (functionCall === "none") {
28023
+ total += FUNCTION_CALL_NONE_TOKEN_OVERHEAD;
28024
+ } else if (typeof functionCall === "object" && functionCall.name) {
28025
+ total += countStringTokens(functionCall.name) + FUNCTION_CALL_NAME_TOKEN_OVERHEAD;
28026
+ }
28027
+ }
28028
+ return total;
28029
+ }
28030
+ var MESSAGE_TOKEN_OVERHEAD, MESSAGE_NAME_TOKEN_OVERHEAD, FUNCTION_ROLE_TOKEN_DISCOUNT, FUNCTION_CALL_METADATA_TOKEN_OVERHEAD, FUNCTION_DEFINITION_TOKEN_OVERHEAD, COMPLETION_REQUEST_TOKEN_OVERHEAD, FUNCTION_CALL_NAME_TOKEN_OVERHEAD, FUNCTION_CALL_NONE_TOKEN_OVERHEAD, SYSTEM_FUNCTION_TOKEN_DEDUCTION, NEWLINE;
28031
+ var init_functionCalling = __esm({
28032
+ "node_modules/gpt-tokenizer/esm/functionCalling.js"() {
28033
+ MESSAGE_TOKEN_OVERHEAD = 3;
28034
+ MESSAGE_NAME_TOKEN_OVERHEAD = 1;
28035
+ FUNCTION_ROLE_TOKEN_DISCOUNT = 2;
28036
+ FUNCTION_CALL_METADATA_TOKEN_OVERHEAD = 3;
28037
+ FUNCTION_DEFINITION_TOKEN_OVERHEAD = 9;
28038
+ COMPLETION_REQUEST_TOKEN_OVERHEAD = 3;
28039
+ FUNCTION_CALL_NAME_TOKEN_OVERHEAD = 4;
28040
+ FUNCTION_CALL_NONE_TOKEN_OVERHEAD = 1;
28041
+ SYSTEM_FUNCTION_TOKEN_DEDUCTION = 4;
28042
+ NEWLINE = "\n";
28043
+ }
28044
+ });
28045
+
27876
28046
  // node_modules/gpt-tokenizer/esm/modelsChatEnabled.gen.js
27877
28047
  var chatEnabledModels;
27878
28048
  var init_modelsChatEnabled_gen = __esm({
@@ -27886,11 +28056,12 @@ var modelsMap_exports = {};
27886
28056
  __export(modelsMap_exports, {
27887
28057
  cl100k_base: () => cl100k_base,
27888
28058
  o200k_base: () => o200k_base,
28059
+ o200k_harmony: () => o200k_harmony,
27889
28060
  p50k_base: () => p50k_base,
27890
28061
  p50k_edit: () => p50k_edit,
27891
28062
  r50k_base: () => r50k_base
27892
28063
  });
27893
- var p50k_base, r50k_base, p50k_edit, cl100k_base, o200k_base;
28064
+ var p50k_base, r50k_base, p50k_edit, cl100k_base, o200k_base, o200k_harmony;
27894
28065
  var init_modelsMap = __esm({
27895
28066
  "node_modules/gpt-tokenizer/esm/modelsMap.js"() {
27896
28067
  p50k_base = [
@@ -27965,11 +28136,15 @@ var init_modelsMap = __esm({
27965
28136
  "davinci-002"
27966
28137
  ];
27967
28138
  o200k_base = [];
28139
+ o200k_harmony = [
28140
+ "gpt-oss-20b",
28141
+ "gpt-oss-120b"
28142
+ ];
27968
28143
  }
27969
28144
  });
27970
28145
 
27971
28146
  // node_modules/gpt-tokenizer/esm/specialTokens.js
27972
- var EndOfText, FimPrefix, FimMiddle, FimSuffix, ImStart, ImEnd, ImSep, EndOfPrompt;
28147
+ var EndOfText, FimPrefix, FimMiddle, FimSuffix, ImStart, ImEnd, ImSep, EndOfPrompt, HarmonyStartOfText, HarmonyStart, HarmonyEnd, HarmonyMessage, HarmonyChannel, HarmonyReturn, HarmonyConstrain, HarmonyCall;
27973
28148
  var init_specialTokens = __esm({
27974
28149
  "node_modules/gpt-tokenizer/esm/specialTokens.js"() {
27975
28150
  EndOfText = "<|endoftext|>";
@@ -27980,6 +28155,14 @@ var init_specialTokens = __esm({
27980
28155
  ImEnd = "<|im_end|>";
27981
28156
  ImSep = "<|im_sep|>";
27982
28157
  EndOfPrompt = "<|endofprompt|>";
28158
+ HarmonyStartOfText = "<|startoftext|>";
28159
+ HarmonyStart = "<|start|>";
28160
+ HarmonyEnd = "<|end|>";
28161
+ HarmonyMessage = "<|message|>";
28162
+ HarmonyChannel = "<|channel|>";
28163
+ HarmonyReturn = "<|return|>";
28164
+ HarmonyConstrain = "<|constrain|>";
28165
+ HarmonyCall = "<|call|>";
27983
28166
  }
27984
28167
  });
27985
28168
 
@@ -28006,11 +28189,16 @@ var init_mapping = __esm({
28006
28189
  });
28007
28190
 
28008
28191
  // node_modules/gpt-tokenizer/esm/encodingParams/constants.js
28009
- var R50K_TOKEN_SPLIT_REGEX, CL_AND_O_TOKEN_SPLIT_PATTERN;
28192
+ var R50K_TOKEN_SPLIT_REGEX, CONTRACTION_SUFFIX_PATTERN, OPTIONAL_CONTRACTION_SUFFIX, CL100K_TOKEN_SPLIT_PATTERN, CL100K_TOKEN_SPLIT_REGEX, O200K_TOKEN_SPLIT_PATTERN, O200K_TOKEN_SPLIT_REGEX;
28010
28193
  var init_constants2 = __esm({
28011
28194
  "node_modules/gpt-tokenizer/esm/encodingParams/constants.js"() {
28012
28195
  R50K_TOKEN_SPLIT_REGEX = /'s|'t|'re|'ve|'m|'ll|'d| ?\p{L}+| ?\p{N}+| ?[^\s\p{L}\p{N}]+|\s+(?!\S)|\s+/gu;
28013
- CL_AND_O_TOKEN_SPLIT_PATTERN = /(?:'s|'t|'re|'ve|'m|'ll|'d)|[^\r\n\p{L}\p{N}]?\p{L}+|\p{N}{1,3}| ?[^\s\p{L}\p{N}]+[\r\n]*|\s*[\r\n]+|\s+(?!\S)|\s+/giu;
28196
+ CONTRACTION_SUFFIX_PATTERN = String.raw`'(?:[sS]|[dD]|[mM]|[tT]|[lL][lL]|[vV][eE]|[rR][eE])`;
28197
+ OPTIONAL_CONTRACTION_SUFFIX = String.raw`(?:${CONTRACTION_SUFFIX_PATTERN})?`;
28198
+ CL100K_TOKEN_SPLIT_PATTERN = String.raw`${CONTRACTION_SUFFIX_PATTERN}|[^\r\n\p{L}\p{N}]?\p{L}+|\p{N}{1,3}| ?[^\s\p{L}\p{N}]+[\r\n]*|\s+$|\s*[\r\n]|\s+(?!\S)|\s`;
28199
+ CL100K_TOKEN_SPLIT_REGEX = new RegExp(CL100K_TOKEN_SPLIT_PATTERN, "gu");
28200
+ O200K_TOKEN_SPLIT_PATTERN = String.raw`[^\r\n\p{L}\p{N}]?[\p{Lu}\p{Lt}\p{Lm}\p{Lo}\p{M}]*[\p{Ll}\p{Lm}\p{Lo}\p{M}]+${OPTIONAL_CONTRACTION_SUFFIX}|[^\r\n\p{L}\p{N}]?[\p{Lu}\p{Lt}\p{Lm}\p{Lo}\p{M}]+[\p{Ll}\p{Lm}\p{Lo}\p{M}]*${OPTIONAL_CONTRACTION_SUFFIX}|\p{N}{1,3}| ?[^\s\p{L}\p{N}]+[\r\n/]*|\s*[\r\n]+|\s+(?!\S)|\s+`;
28201
+ O200K_TOKEN_SPLIT_REGEX = new RegExp(O200K_TOKEN_SPLIT_PATTERN, "gu");
28014
28202
  }
28015
28203
  });
28016
28204
 
@@ -28027,7 +28215,7 @@ function Cl100KBase(bytePairRankDecoder) {
28027
28215
  [EndOfPrompt, 100276]
28028
28216
  ]);
28029
28217
  return {
28030
- tokenSplitRegex: CL_AND_O_TOKEN_SPLIT_PATTERN,
28218
+ tokenSplitRegex: CL100K_TOKEN_SPLIT_REGEX,
28031
28219
  bytePairRankDecoder,
28032
28220
  specialTokensEncoder: specialTokenMapping
28033
28221
  };
@@ -28041,26 +28229,69 @@ var init_cl100k_base = __esm({
28041
28229
 
28042
28230
  // node_modules/gpt-tokenizer/esm/encodingParams/o200k_base.js
28043
28231
  function O200KBase(bytePairRankDecoder) {
28044
- const specialTokenMapping = /* @__PURE__ */ new Map([
28045
- [EndOfText, 199999],
28046
- [FimPrefix, 2e5],
28047
- [FimMiddle, 200001],
28048
- [FimSuffix, 200002],
28049
- [ImStart, 200003],
28050
- [ImEnd, 200004],
28051
- [ImSep, 200005],
28052
- [EndOfPrompt, 200006]
28053
- ]);
28054
28232
  return {
28055
- tokenSplitRegex: CL_AND_O_TOKEN_SPLIT_PATTERN,
28233
+ tokenSplitRegex: O200K_TOKEN_SPLIT_REGEX,
28056
28234
  bytePairRankDecoder,
28057
- specialTokensEncoder: specialTokenMapping
28235
+ specialTokensEncoder: createO200KSpecialTokenMap()
28058
28236
  };
28059
28237
  }
28238
+ var O200K_BASE_SPECIAL_TOKEN_ENTRIES, createO200KSpecialTokenMap;
28060
28239
  var init_o200k_base2 = __esm({
28061
28240
  "node_modules/gpt-tokenizer/esm/encodingParams/o200k_base.js"() {
28062
28241
  init_specialTokens();
28063
28242
  init_constants2();
28243
+ O200K_BASE_SPECIAL_TOKEN_ENTRIES = [
28244
+ [EndOfText, 199999],
28245
+ [FimPrefix, 2e5],
28246
+ [FimMiddle, 200001],
28247
+ [FimSuffix, 200002],
28248
+ [ImStart, 200003],
28249
+ [ImEnd, 200004],
28250
+ [ImSep, 200005],
28251
+ [EndOfPrompt, 200006]
28252
+ ];
28253
+ createO200KSpecialTokenMap = () => new Map(O200K_BASE_SPECIAL_TOKEN_ENTRIES);
28254
+ }
28255
+ });
28256
+
28257
+ // node_modules/gpt-tokenizer/esm/encodingParams/o200k_harmony.js
28258
+ function O200KHarmony(bytePairRankDecoder) {
28259
+ const specialTokensEncoder = new Map(STATIC_SPECIAL_TOKEN_ENTRIES);
28260
+ for (let tokenId = RESERVED_TOKEN_RANGE_START; tokenId < RESERVED_TOKEN_RANGE_END; tokenId += 1) {
28261
+ specialTokensEncoder.set(`<|reserved_${tokenId}|>`, tokenId);
28262
+ }
28263
+ specialTokensEncoder.set(EndOfPrompt, 200018);
28264
+ return {
28265
+ tokenSplitRegex: O200K_TOKEN_SPLIT_REGEX,
28266
+ bytePairRankDecoder,
28267
+ specialTokensEncoder,
28268
+ chatFormatter: "harmony"
28269
+ };
28270
+ }
28271
+ var RESERVED_TOKEN_RANGE_START, RESERVED_TOKEN_RANGE_END, STATIC_SPECIAL_TOKEN_ENTRIES;
28272
+ var init_o200k_harmony = __esm({
28273
+ "node_modules/gpt-tokenizer/esm/encodingParams/o200k_harmony.js"() {
28274
+ init_specialTokens();
28275
+ init_constants2();
28276
+ RESERVED_TOKEN_RANGE_START = 200013;
28277
+ RESERVED_TOKEN_RANGE_END = 201088;
28278
+ STATIC_SPECIAL_TOKEN_ENTRIES = [
28279
+ [HarmonyStartOfText, 199998],
28280
+ [EndOfText, 199999],
28281
+ ["<|reserved_200000|>", 2e5],
28282
+ ["<|reserved_200001|>", 200001],
28283
+ [HarmonyReturn, 200002],
28284
+ [HarmonyConstrain, 200003],
28285
+ ["<|reserved_200004|>", 200004],
28286
+ [HarmonyChannel, 200005],
28287
+ [HarmonyStart, 200006],
28288
+ [HarmonyEnd, 200007],
28289
+ [HarmonyMessage, 200008],
28290
+ ["<|reserved_200009|>", 200009],
28291
+ ["<|reserved_200010|>", 200010],
28292
+ ["<|reserved_200011|>", 200011],
28293
+ [HarmonyCall, 200012]
28294
+ ];
28064
28295
  }
28065
28296
  });
28066
28297
 
@@ -28134,6 +28365,8 @@ function getEncodingParams(encodingName, getMergeableRanks) {
28134
28365
  return Cl100KBase(mergeableBytePairRanks);
28135
28366
  case "o200k_base":
28136
28367
  return O200KBase(mergeableBytePairRanks);
28368
+ case "o200k_harmony":
28369
+ return O200KHarmony(mergeableBytePairRanks);
28137
28370
  default:
28138
28371
  throw new Error(`Unknown encoding name: ${encodingName}`);
28139
28372
  }
@@ -28142,6 +28375,7 @@ var init_modelParams = __esm({
28142
28375
  "node_modules/gpt-tokenizer/esm/modelParams.js"() {
28143
28376
  init_cl100k_base();
28144
28377
  init_o200k_base2();
28378
+ init_o200k_harmony();
28145
28379
  init_p50k_base();
28146
28380
  init_p50k_edit();
28147
28381
  init_r50k_base();
@@ -28154,6 +28388,7 @@ var init_GptEncoding = __esm({
28154
28388
  "node_modules/gpt-tokenizer/esm/GptEncoding.js"() {
28155
28389
  init_BytePairEncodingCore();
28156
28390
  init_constants();
28391
+ init_functionCalling();
28157
28392
  init_mapping();
28158
28393
  init_modelParams();
28159
28394
  init_specialTokens();
@@ -28172,8 +28407,10 @@ var init_GptEncoding = __esm({
28172
28407
  specialTokensSet;
28173
28408
  allSpecialTokenRegex;
28174
28409
  defaultSpecialTokenConfig;
28410
+ chatFormatter;
28411
+ countChatCompletionTokens;
28175
28412
  vocabularySize;
28176
- constructor({ bytePairRankDecoder: mergeableBytePairRanks, specialTokensEncoder, expectedVocabularySize, modelName, modelSpec, ...rest }) {
28413
+ constructor({ bytePairRankDecoder: mergeableBytePairRanks, specialTokensEncoder, expectedVocabularySize, modelName, modelSpec, chatFormatter, ...rest }) {
28177
28414
  this.specialTokensEncoder = specialTokensEncoder;
28178
28415
  this.specialTokensSet = new Set(this.specialTokensEncoder.keys());
28179
28416
  this.allSpecialTokenRegex = getSpecialTokenRegex(this.specialTokensSet);
@@ -28206,8 +28443,69 @@ var init_GptEncoding = __esm({
28206
28443
  this.setMergeCacheSize = this.setMergeCacheSize.bind(this);
28207
28444
  this.clearMergeCache = this.clearMergeCache.bind(this);
28208
28445
  this.estimateCost = this.estimateCost.bind(this);
28446
+ if (modelSpec?.supported_features?.includes("function_calling")) {
28447
+ this.countChatCompletionTokens = this.countChatCompletionTokensInternal.bind(this);
28448
+ }
28209
28449
  this.modelName = modelName;
28210
28450
  this.modelSpec = modelSpec;
28451
+ this.chatFormatter = chatFormatter ?? "chatml";
28452
+ }
28453
+ *encodeHarmonyChatGenerator(chat, encodeOptions) {
28454
+ const harmonyStart = this.specialTokensEncoder.get(HarmonyStart);
28455
+ const harmonyMessage = this.specialTokensEncoder.get(HarmonyMessage);
28456
+ const harmonyEnd = this.specialTokensEncoder.get(HarmonyEnd);
28457
+ const harmonyReturn = this.specialTokensEncoder.get(HarmonyReturn);
28458
+ const harmonyCall = this.specialTokensEncoder.get(HarmonyCall);
28459
+ const harmonyChannel = this.specialTokensEncoder.get(HarmonyChannel);
28460
+ const harmonyConstrain = this.specialTokensEncoder.get(HarmonyConstrain);
28461
+ if (harmonyStart === void 0 || harmonyMessage === void 0 || harmonyEnd === void 0 || harmonyReturn === void 0 || harmonyCall === void 0 || harmonyChannel === void 0 || harmonyConstrain === void 0) {
28462
+ throw new Error("Harmony chat format requires dedicated special tokens.");
28463
+ }
28464
+ const encodeHeaderText = (text) => text.length > 0 ? this.encode(text) : [];
28465
+ const resolveTerminatorToken = (terminator) => {
28466
+ switch (terminator) {
28467
+ case "<|return|>":
28468
+ return harmonyReturn;
28469
+ case "<|call|>":
28470
+ return harmonyCall;
28471
+ // eslint-disable-next-line unicorn/no-useless-switch-case
28472
+ case "<|end|>":
28473
+ default:
28474
+ return harmonyEnd;
28475
+ }
28476
+ };
28477
+ for (const message of chat) {
28478
+ if (message.content === void 0) {
28479
+ throw new Error("Content must be defined for all messages.");
28480
+ }
28481
+ const roleOrName = message.name ?? message.role ?? "user";
28482
+ yield [harmonyStart];
28483
+ yield encodeHeaderText(roleOrName);
28484
+ const recipientInRole = message.recipient && (message.recipientPlacement === "role" || !message.channel);
28485
+ const recipientInChannel = message.recipient && !recipientInRole;
28486
+ if (recipientInRole) {
28487
+ yield encodeHeaderText(` to=${message.recipient}`);
28488
+ }
28489
+ if (message.channel) {
28490
+ yield [harmonyChannel];
28491
+ yield encodeHeaderText(message.channel);
28492
+ if (recipientInChannel) {
28493
+ yield encodeHeaderText(` to=${message.recipient}`);
28494
+ }
28495
+ }
28496
+ if (message.constraint) {
28497
+ yield [harmonyConstrain];
28498
+ yield encodeHeaderText(message.constraint);
28499
+ }
28500
+ yield [harmonyMessage];
28501
+ yield* this.encodeGenerator(message.content, encodeOptions);
28502
+ yield [resolveTerminatorToken(message.terminator)];
28503
+ }
28504
+ const assistantPrime = encodeOptions?.primeWithAssistantResponse ?? "assistant";
28505
+ if (assistantPrime.length > 0) {
28506
+ yield [harmonyStart];
28507
+ yield encodeHeaderText(assistantPrime);
28508
+ }
28211
28509
  }
28212
28510
  static getEncodingApi(encodingName, getMergeableRanks) {
28213
28511
  const modelParams = getEncodingParams(encodingName, getMergeableRanks);
@@ -28280,9 +28578,16 @@ var init_GptEncoding = __esm({
28280
28578
  throw new Error("Model name must be provided either during initialization or passed in to the method.");
28281
28579
  }
28282
28580
  const params = chatModelParams[model];
28581
+ if (!params) {
28582
+ throw new Error(`Model '${model}' does not support chat.`);
28583
+ }
28584
+ if (this.chatFormatter === "harmony") {
28585
+ yield* this.encodeHarmonyChatGenerator(chat, encodeOptions);
28586
+ return;
28587
+ }
28283
28588
  const chatStartToken = this.specialTokensEncoder.get(ImStart);
28284
28589
  const chatEndToken = this.specialTokensEncoder.get(ImEnd);
28285
- if (!params || chatStartToken === void 0 || chatEndToken === void 0) {
28590
+ if (chatStartToken === void 0 || chatEndToken === void 0) {
28286
28591
  throw new Error(`Model '${model}' does not support chat.`);
28287
28592
  }
28288
28593
  const allowedSpecial = /* @__PURE__ */ new Set([ImSep]);
@@ -28305,8 +28610,11 @@ var init_GptEncoding = __esm({
28305
28610
  yield [chatEndToken];
28306
28611
  yield encodedMessageSeparator;
28307
28612
  }
28308
- yield [chatStartToken];
28309
- yield* this.encodeGenerator("assistant", encodeOptions);
28613
+ const assistantPrime = encodeOptions?.primeWithAssistantResponse ?? "assistant";
28614
+ if (assistantPrime.length > 0) {
28615
+ yield [chatStartToken];
28616
+ yield* this.encodeGenerator(assistantPrime, encodeOptions);
28617
+ }
28310
28618
  if (encodedRoleSeparator.length > 0) {
28311
28619
  yield encodedRoleSeparator;
28312
28620
  }
@@ -28364,6 +28672,15 @@ var init_GptEncoding = __esm({
28364
28672
  }
28365
28673
  return count;
28366
28674
  }
28675
+ countStringTokens(text) {
28676
+ if (!text) {
28677
+ return 0;
28678
+ }
28679
+ return this.bytePairEncodingCoreProcessor.countNative(text);
28680
+ }
28681
+ countChatCompletionTokensInternal(request) {
28682
+ return computeChatCompletionTokenCount(request, (text) => this.countStringTokens(text));
28683
+ }
28367
28684
  setMergeCacheSize(size) {
28368
28685
  this.bytePairEncodingCoreProcessor.setMergeCacheSize(size);
28369
28686
  }
@@ -29055,10 +29372,22 @@ function extractThinkingContent(xmlString) {
29055
29372
  return thinkingMatch ? thinkingMatch[1].trim() : null;
29056
29373
  }
29057
29374
  function checkAttemptCompleteRecovery(cleanedXmlString, validTools = []) {
29058
- const attemptCompletionMatch = cleanedXmlString.match(/<attempt_completion>([\s\S]*?)(?:<\/attempt_completion>|$)/);
29059
- if (attemptCompletionMatch) {
29060
- const content = attemptCompletionMatch[1].trim();
29061
- const hasClosingTag = cleanedXmlString.includes("</attempt_completion>");
29375
+ const openTagIndex = cleanedXmlString.indexOf("<attempt_completion>");
29376
+ if (openTagIndex !== -1) {
29377
+ const afterOpenTag = cleanedXmlString.substring(openTagIndex + "<attempt_completion>".length);
29378
+ const closeTagIndex = cleanedXmlString.lastIndexOf("</attempt_completion>");
29379
+ let content;
29380
+ let hasClosingTag = false;
29381
+ if (closeTagIndex !== -1 && closeTagIndex >= openTagIndex + "<attempt_completion>".length) {
29382
+ content = cleanedXmlString.substring(
29383
+ openTagIndex + "<attempt_completion>".length,
29384
+ closeTagIndex
29385
+ ).trim();
29386
+ hasClosingTag = true;
29387
+ } else {
29388
+ content = afterOpenTag.trim();
29389
+ hasClosingTag = false;
29390
+ }
29062
29391
  if (content) {
29063
29392
  return {
29064
29393
  toolName: "attempt_completion",
@@ -33375,7 +33704,15 @@ function parseXmlToolCall(xmlString, validTools = DEFAULT_VALID_TOOLS) {
33375
33704
  if (openIndex === -1) {
33376
33705
  continue;
33377
33706
  }
33378
- let closeIndex = xmlString.indexOf(closeTag, openIndex + openTag.length);
33707
+ let closeIndex;
33708
+ if (toolName === "attempt_completion") {
33709
+ closeIndex = xmlString.lastIndexOf(closeTag);
33710
+ if (closeIndex !== -1 && closeIndex <= openIndex + openTag.length) {
33711
+ closeIndex = -1;
33712
+ }
33713
+ } else {
33714
+ closeIndex = xmlString.indexOf(closeTag, openIndex + openTag.length);
33715
+ }
33379
33716
  let hasClosingTag = closeIndex !== -1;
33380
33717
  if (closeIndex === -1) {
33381
33718
  closeIndex = xmlString.length;
@@ -77349,6 +77686,8 @@ __export(schemaUtils_exports, {
77349
77686
  createSchemaDefinitionCorrectionPrompt: () => createSchemaDefinitionCorrectionPrompt,
77350
77687
  decodeHtmlEntities: () => decodeHtmlEntities,
77351
77688
  extractMermaidFromMarkdown: () => extractMermaidFromMarkdown,
77689
+ generateExampleFromSchema: () => generateExampleFromSchema,
77690
+ generateSchemaInstructions: () => generateSchemaInstructions,
77352
77691
  isJsonSchema: () => isJsonSchema,
77353
77692
  isJsonSchemaDefinition: () => isJsonSchemaDefinition,
77354
77693
  isMermaidSchema: () => isMermaidSchema,
@@ -77361,6 +77700,63 @@ __export(schemaUtils_exports, {
77361
77700
  validateMermaidResponse: () => validateMermaidResponse,
77362
77701
  validateXmlResponse: () => validateXmlResponse
77363
77702
  });
77703
+ function generateExampleFromSchema(schema, options = {}) {
77704
+ const { debug = false } = options;
77705
+ try {
77706
+ const parsedSchema = typeof schema === "string" ? JSON.parse(schema) : schema;
77707
+ if (parsedSchema.type !== "object" || !parsedSchema.properties) {
77708
+ return null;
77709
+ }
77710
+ const exampleObj = {};
77711
+ for (const [key, value] of Object.entries(parsedSchema.properties)) {
77712
+ if (value.type === "boolean") {
77713
+ exampleObj[key] = false;
77714
+ } else if (value.type === "number") {
77715
+ exampleObj[key] = 0;
77716
+ } else if (value.type === "string") {
77717
+ exampleObj[key] = value.description || "your answer here";
77718
+ } else if (value.type === "array") {
77719
+ exampleObj[key] = [];
77720
+ } else {
77721
+ exampleObj[key] = {};
77722
+ }
77723
+ }
77724
+ return exampleObj;
77725
+ } catch (e3) {
77726
+ if (debug) {
77727
+ console.error("[DEBUG] generateExampleFromSchema: Failed to parse schema:", e3.message);
77728
+ }
77729
+ return null;
77730
+ }
77731
+ }
77732
+ function generateSchemaInstructions(schema, options = {}) {
77733
+ const { debug = false } = options;
77734
+ let instructions = "\n\nIMPORTANT: When you provide your final answer using attempt_completion, you MUST format it as valid JSON matching this schema:\n\n";
77735
+ try {
77736
+ const parsedSchema = typeof schema === "string" ? JSON.parse(schema) : schema;
77737
+ instructions += `${JSON.stringify(parsedSchema, null, 2)}
77738
+
77739
+ `;
77740
+ const exampleObj = generateExampleFromSchema(parsedSchema, { debug });
77741
+ if (exampleObj) {
77742
+ instructions += `Example:
77743
+ <attempt_completion>
77744
+ ${JSON.stringify(exampleObj, null, 2)}
77745
+ </attempt_completion>
77746
+
77747
+ `;
77748
+ }
77749
+ } catch (e3) {
77750
+ if (debug) {
77751
+ console.error("[DEBUG] generateSchemaInstructions: Failed to parse schema:", e3.message);
77752
+ }
77753
+ instructions += `${schema}
77754
+
77755
+ `;
77756
+ }
77757
+ instructions += "Your response inside attempt_completion must be ONLY valid JSON - no plain text, no explanations, no markdown.";
77758
+ return instructions;
77759
+ }
77364
77760
  function enforceNoAdditionalProperties(schema) {
77365
77761
  if (!schema || typeof schema !== "object") {
77366
77762
  return schema;
@@ -80064,6 +80460,170 @@ var init_FallbackManager = __esm({
80064
80460
  }
80065
80461
  });
80066
80462
 
80463
+ // src/agent/contextCompactor.js
80464
+ var contextCompactor_exports = {};
80465
+ __export(contextCompactor_exports, {
80466
+ calculateCompactionStats: () => calculateCompactionStats,
80467
+ compactMessages: () => compactMessages,
80468
+ handleContextLimitError: () => handleContextLimitError,
80469
+ identifyMessageSegments: () => identifyMessageSegments,
80470
+ isContextLimitError: () => isContextLimitError
80471
+ });
80472
+ function isContextLimitError(error2) {
80473
+ if (!error2) return false;
80474
+ const errorMessage = (typeof error2 === "string" ? error2 : error2?.message || "").toLowerCase();
80475
+ const errorString = error2.toString().toLowerCase();
80476
+ for (const pattern of CONTEXT_LIMIT_ERROR_PATTERNS) {
80477
+ const lowerPattern = pattern.toLowerCase();
80478
+ if (errorMessage.includes(lowerPattern) || errorString.includes(lowerPattern)) {
80479
+ return true;
80480
+ }
80481
+ }
80482
+ return false;
80483
+ }
80484
+ function identifyMessageSegments(messages) {
80485
+ const segments = [];
80486
+ let currentSegment = null;
80487
+ for (let i3 = 0; i3 < messages.length; i3++) {
80488
+ const msg = messages[i3];
80489
+ if (msg.role === "system") {
80490
+ continue;
80491
+ }
80492
+ if (msg.role === "user") {
80493
+ const content = typeof msg.content === "string" ? msg.content : "";
80494
+ const isToolResult = content.includes("<tool_result>");
80495
+ if (isToolResult && currentSegment) {
80496
+ currentSegment.finalIndex = i3;
80497
+ segments.push(currentSegment);
80498
+ currentSegment = null;
80499
+ } else {
80500
+ if (currentSegment) {
80501
+ segments.push(currentSegment);
80502
+ }
80503
+ currentSegment = {
80504
+ userIndex: i3,
80505
+ monologueIndices: [],
80506
+ finalIndex: null
80507
+ };
80508
+ }
80509
+ }
80510
+ if (msg.role === "assistant" && currentSegment) {
80511
+ const content = typeof msg.content === "string" ? msg.content : "";
80512
+ if (content.includes("<attempt_completion>") || content.includes("attempt_completion")) {
80513
+ currentSegment.monologueIndices.push(i3);
80514
+ currentSegment.finalIndex = i3;
80515
+ segments.push(currentSegment);
80516
+ currentSegment = null;
80517
+ } else {
80518
+ currentSegment.monologueIndices.push(i3);
80519
+ }
80520
+ }
80521
+ }
80522
+ if (currentSegment) {
80523
+ segments.push(currentSegment);
80524
+ }
80525
+ return segments;
80526
+ }
80527
+ function compactMessages(messages, options = {}) {
80528
+ const {
80529
+ keepLastSegment = true,
80530
+ minSegmentsToKeep = 1
80531
+ } = options;
80532
+ if (!messages || messages.length === 0) {
80533
+ return messages;
80534
+ }
80535
+ const segments = identifyMessageSegments(messages);
80536
+ if (segments.length === 0) {
80537
+ return messages;
80538
+ }
80539
+ const segmentsToPreserve = keepLastSegment ? Math.max(minSegmentsToKeep, 1) : minSegmentsToKeep;
80540
+ const compactableSegments = segments.slice(0, -segmentsToPreserve);
80541
+ const preservedSegments = segments.slice(-segmentsToPreserve);
80542
+ const indicesToKeep = /* @__PURE__ */ new Set();
80543
+ messages.forEach((msg, idx) => {
80544
+ if (msg.role === "system") {
80545
+ indicesToKeep.add(idx);
80546
+ }
80547
+ });
80548
+ compactableSegments.forEach((segment) => {
80549
+ indicesToKeep.add(segment.userIndex);
80550
+ if (segment.finalIndex !== null) {
80551
+ indicesToKeep.add(segment.finalIndex);
80552
+ }
80553
+ });
80554
+ preservedSegments.forEach((segment) => {
80555
+ indicesToKeep.add(segment.userIndex);
80556
+ segment.monologueIndices.forEach((idx) => indicesToKeep.add(idx));
80557
+ if (segment.finalIndex !== null) {
80558
+ indicesToKeep.add(segment.finalIndex);
80559
+ }
80560
+ });
80561
+ const compactedMessages = messages.filter((_2, idx) => indicesToKeep.has(idx));
80562
+ return compactedMessages;
80563
+ }
80564
+ function calculateCompactionStats(originalMessages, compactedMessages) {
80565
+ const originalCount = originalMessages.length;
80566
+ const compactedCount = compactedMessages.length;
80567
+ const removed = originalCount - compactedCount;
80568
+ const reductionPercent = originalCount > 0 ? (removed / originalCount * 100).toFixed(1) : 0;
80569
+ const estimateTokens = (msgs) => {
80570
+ return msgs.reduce((sum, msg) => {
80571
+ const content = typeof msg.content === "string" ? msg.content : JSON.stringify(msg.content);
80572
+ return sum + Math.ceil(content.length / 4);
80573
+ }, 0);
80574
+ };
80575
+ const originalTokens = estimateTokens(originalMessages);
80576
+ const compactedTokens = estimateTokens(compactedMessages);
80577
+ const tokensSaved = originalTokens - compactedTokens;
80578
+ return {
80579
+ originalCount,
80580
+ compactedCount,
80581
+ removed,
80582
+ reductionPercent: parseFloat(reductionPercent),
80583
+ originalTokens,
80584
+ compactedTokens,
80585
+ tokensSaved
80586
+ };
80587
+ }
80588
+ function handleContextLimitError(error2, messages, options = {}) {
80589
+ if (!isContextLimitError(error2)) {
80590
+ return null;
80591
+ }
80592
+ const compactedMessages = compactMessages(messages, options);
80593
+ const stats = calculateCompactionStats(messages, compactedMessages);
80594
+ return {
80595
+ compacted: true,
80596
+ messages: compactedMessages,
80597
+ stats
80598
+ };
80599
+ }
80600
+ var CONTEXT_LIMIT_ERROR_PATTERNS;
80601
+ var init_contextCompactor = __esm({
80602
+ "src/agent/contextCompactor.js"() {
80603
+ "use strict";
80604
+ CONTEXT_LIMIT_ERROR_PATTERNS = [
80605
+ // Anthropic
80606
+ "context_length_exceeded",
80607
+ "prompt is too long",
80608
+ // OpenAI
80609
+ "maximum context length",
80610
+ "context length is",
80611
+ // Google/Gemini
80612
+ "input token count exceeds",
80613
+ "token limit exceeded",
80614
+ // Generic patterns
80615
+ "context window",
80616
+ "too many tokens",
80617
+ "token limit",
80618
+ "context limit",
80619
+ "exceed",
80620
+ // Catches "exceeds", "exceed maximum", etc.
80621
+ "over the limit",
80622
+ "maximum tokens"
80623
+ ];
80624
+ }
80625
+ });
80626
+
80067
80627
  // src/agent/ProbeAgent.js
80068
80628
  var ProbeAgent_exports = {};
80069
80629
  __export(ProbeAgent_exports, {
@@ -80098,6 +80658,7 @@ var init_ProbeAgent = __esm({
80098
80658
  init_mcp();
80099
80659
  init_RetryManager();
80100
80660
  init_FallbackManager();
80661
+ init_contextCompactor();
80101
80662
  import_dotenv.default.config();
80102
80663
  MAX_TOOL_ITERATIONS = (() => {
80103
80664
  const val = parseInt(process.env.MAX_TOOL_ITERATIONS || "30", 10);
@@ -80133,6 +80694,8 @@ var init_ProbeAgent = __esm({
80133
80694
  * @param {Array} [options.mcpServers] - Deprecated, use mcpConfig instead
80134
80695
  * @param {Object} [options.storageAdapter] - Custom storage adapter for history management
80135
80696
  * @param {Object} [options.hooks] - Hook callbacks for events (e.g., {'tool:start': callback})
80697
+ * @param {Array<string>|null} [options.allowedTools] - List of allowed tool names. Use ['*'] for all tools (default), [] or null for no tools (raw AI mode), or specific tool names like ['search', 'query', 'extract']. Supports exclusion with '!' prefix (e.g., ['*', '!bash'])
80698
+ * @param {boolean} [options.disableTools=false] - Convenience flag to disable all tools (equivalent to allowedTools: []). Takes precedence over allowedTools if set.
80136
80699
  * @param {Object} [options.retry] - Retry configuration
80137
80700
  * @param {number} [options.retry.maxRetries=3] - Maximum retry attempts per provider
80138
80701
  * @param {number} [options.retry.initialDelay=1000] - Initial delay in ms
@@ -80166,6 +80729,8 @@ var init_ProbeAgent = __esm({
80166
80729
  this.maxIterations = options.maxIterations || null;
80167
80730
  this.disableMermaidValidation = !!options.disableMermaidValidation;
80168
80731
  this.disableJsonValidation = !!options.disableJsonValidation;
80732
+ const effectiveAllowedTools = options.disableTools ? [] : options.allowedTools;
80733
+ this.allowedTools = this._parseAllowedTools(effectiveAllowedTools);
80169
80734
  this.storageAdapter = options.storageAdapter || new InMemoryStorageAdapter();
80170
80735
  this.hooks = new HookManager();
80171
80736
  if (options.hooks) {
@@ -80209,6 +80774,61 @@ var init_ProbeAgent = __esm({
80209
80774
  this.fallbackManager = null;
80210
80775
  this.initializeModel();
80211
80776
  }
80777
+ /**
80778
+ * Parse allowedTools configuration
80779
+ * @param {Array<string>|null|undefined} allowedTools - Tool filtering configuration
80780
+ * @returns {Object} Parsed configuration with isEnabled method
80781
+ * @private
80782
+ */
80783
+ _parseAllowedTools(allowedTools) {
80784
+ const matchesPattern2 = (toolName, pattern) => {
80785
+ if (!pattern.includes("*")) {
80786
+ return toolName === pattern;
80787
+ }
80788
+ const regexPattern = pattern.replace(/\*/g, ".*");
80789
+ return new RegExp(`^${regexPattern}$`).test(toolName);
80790
+ };
80791
+ if (!allowedTools || Array.isArray(allowedTools) && allowedTools.includes("*")) {
80792
+ const exclusions = Array.isArray(allowedTools) ? allowedTools.filter((t3) => t3.startsWith("!")).map((t3) => t3.slice(1)) : [];
80793
+ return {
80794
+ mode: "all",
80795
+ exclusions,
80796
+ isEnabled: (toolName) => !exclusions.some((pattern) => matchesPattern2(toolName, pattern))
80797
+ };
80798
+ }
80799
+ if (Array.isArray(allowedTools) && allowedTools.length === 0) {
80800
+ return {
80801
+ mode: "none",
80802
+ isEnabled: () => false
80803
+ };
80804
+ }
80805
+ const allowedPatterns = allowedTools.filter((t3) => !t3.startsWith("!"));
80806
+ return {
80807
+ mode: "whitelist",
80808
+ allowed: allowedPatterns,
80809
+ isEnabled: (toolName) => allowedPatterns.some((pattern) => matchesPattern2(toolName, pattern))
80810
+ };
80811
+ }
80812
+ /**
80813
+ * Check if an MCP tool is allowed based on allowedTools configuration
80814
+ * Uses mcp__ prefix convention (like Claude Code)
80815
+ * @param {string} toolName - The MCP tool name (without mcp__ prefix)
80816
+ * @returns {boolean} - Whether the tool is allowed
80817
+ * @private
80818
+ */
80819
+ _isMcpToolAllowed(toolName) {
80820
+ const mcpToolName = `mcp__${toolName}`;
80821
+ return this.allowedTools.isEnabled(mcpToolName) || this.allowedTools.isEnabled(toolName);
80822
+ }
80823
+ /**
80824
+ * Filter MCP tools based on allowedTools configuration
80825
+ * @param {string[]} mcpToolNames - Array of MCP tool names
80826
+ * @returns {string[]} - Filtered array of allowed MCP tool names
80827
+ * @private
80828
+ */
80829
+ _filterMcpTools(mcpToolNames) {
80830
+ return mcpToolNames.filter((toolName) => this._isMcpToolAllowed(toolName));
80831
+ }
80212
80832
  /**
80213
80833
  * Initialize the agent asynchronously (must be called after constructor)
80214
80834
  * This method initializes MCP and merges MCP tools into the tool list, and loads history from storage
@@ -80235,7 +80855,11 @@ var init_ProbeAgent = __esm({
80235
80855
  if (this.mcpBridge) {
80236
80856
  const mcpTools = this.mcpBridge.mcpTools || {};
80237
80857
  for (const [toolName, toolImpl] of Object.entries(mcpTools)) {
80238
- this.toolImplementations[toolName] = toolImpl;
80858
+ if (this._isMcpToolAllowed(toolName)) {
80859
+ this.toolImplementations[toolName] = toolImpl;
80860
+ } else if (this.debug) {
80861
+ console.error(`[DEBUG] MCP tool '${toolName}' filtered out by allowedTools`);
80862
+ }
80239
80863
  }
80240
80864
  }
80241
80865
  if (this.debug) {
@@ -80855,7 +81479,11 @@ var init_ProbeAgent = __esm({
80855
81479
  if (this.mcpBridge) {
80856
81480
  const mcpTools = this.mcpBridge.mcpTools || {};
80857
81481
  for (const [toolName, toolImpl] of Object.entries(mcpTools)) {
80858
- this.toolImplementations[toolName] = toolImpl;
81482
+ if (this._isMcpToolAllowed(toolName)) {
81483
+ this.toolImplementations[toolName] = toolImpl;
81484
+ } else if (this.debug) {
81485
+ console.error(`[DEBUG] MCP tool '${toolName}' filtered out by allowedTools`);
81486
+ }
80859
81487
  }
80860
81488
  }
80861
81489
  } catch (error2) {
@@ -80865,27 +81493,49 @@ var init_ProbeAgent = __esm({
80865
81493
  }
80866
81494
  }
80867
81495
  }
80868
- let toolDefinitions = `
80869
- ${searchToolDefinition}
80870
- ${queryToolDefinition}
80871
- ${extractToolDefinition}
80872
- ${listFilesToolDefinition}
80873
- ${searchFilesToolDefinition}
80874
- ${attemptCompletionToolDefinition}
81496
+ let toolDefinitions = "";
81497
+ const isToolAllowed = (toolName) => this.allowedTools.isEnabled(toolName);
81498
+ if (isToolAllowed("search")) {
81499
+ toolDefinitions += `${searchToolDefinition}
80875
81500
  `;
80876
- if (this.allowEdit) {
81501
+ }
81502
+ if (isToolAllowed("query")) {
81503
+ toolDefinitions += `${queryToolDefinition}
81504
+ `;
81505
+ }
81506
+ if (isToolAllowed("extract")) {
81507
+ toolDefinitions += `${extractToolDefinition}
81508
+ `;
81509
+ }
81510
+ if (isToolAllowed("listFiles")) {
81511
+ toolDefinitions += `${listFilesToolDefinition}
81512
+ `;
81513
+ }
81514
+ if (isToolAllowed("searchFiles")) {
81515
+ toolDefinitions += `${searchFilesToolDefinition}
81516
+ `;
81517
+ }
81518
+ if (this.allowEdit && isToolAllowed("implement")) {
80877
81519
  toolDefinitions += `${implementToolDefinition}
80878
81520
  `;
81521
+ }
81522
+ if (this.allowEdit && isToolAllowed("edit")) {
80879
81523
  toolDefinitions += `${editToolDefinition}
80880
81524
  `;
81525
+ }
81526
+ if (this.allowEdit && isToolAllowed("create")) {
80881
81527
  toolDefinitions += `${createToolDefinition}
80882
81528
  `;
80883
81529
  }
80884
- if (this.enableBash) {
81530
+ if (this.enableBash && isToolAllowed("bash")) {
80885
81531
  toolDefinitions += `${bashToolDefinition}
80886
81532
  `;
80887
81533
  }
80888
- if (this.enableDelegate) {
81534
+ if (isToolAllowed("attempt_completion")) {
81535
+ toolDefinitions += `${attemptCompletionToolDefinition}
81536
+ `;
81537
+ }
81538
+ if (this.enableDelegate && isToolAllowed("delegate")) {
80889
81539
  toolDefinitions += `${delegateToolDefinition}
80890
81540
  `;
80891
81541
  }
@@ -81047,11 +81697,14 @@ ${xmlToolGuidelines}
81047
81697
  ${toolDefinitions}
81048
81698
  `;
81049
81699
  if (this.mcpBridge && this.mcpBridge.getToolNames().length > 0) {
81050
- systemMessage += `
81700
+ const allMcpTools = this.mcpBridge.getToolNames();
81701
+ const allowedMcpTools = this._filterMcpTools(allMcpTools);
81702
+ if (allowedMcpTools.length > 0) {
81703
+ systemMessage += `
81051
81704
  ## MCP Tools (JSON parameters in <params> tag)
81052
81705
  `;
81053
- systemMessage += this.mcpBridge.getXmlToolDefinitions();
81054
- systemMessage += `
81706
+ systemMessage += this.mcpBridge.getXmlToolDefinitions(allowedMcpTools);
81707
+ systemMessage += `
81055
81708
 
81056
81709
  For MCP tools, use JSON format within the params tag, e.g.:
81057
81710
  <mcp_tool>
@@ -81060,6 +81713,7 @@ For MCP tools, use JSON format within the params tag, e.g.:
81060
81713
  </params>
81061
81714
  </mcp_tool>
81062
81715
  `;
81716
+ }
81063
81717
  }
81064
81718
  const searchDirectory = this.allowedFolders.length > 0 ? this.allowedFolders[0] : process.cwd();
81065
81719
  if (this.debug) {
@@ -81132,9 +81786,14 @@ You are working with a repository located at: ${searchDirectory}
81132
81786
  });
81133
81787
  const systemMessage = await this.getSystemMessage();
81134
81788
  let userMessage = { role: "user", content: message.trim() };
81789
+ if (options.schema && !options._schemaFormatted) {
81790
+ const schemaInstructions = generateSchemaInstructions(options.schema, { debug: this.debug });
81791
+ userMessage.content = message.trim() + schemaInstructions;
81792
+ }
81135
81793
  if (images && images.length > 0) {
81794
+ const textContent = userMessage.content;
81136
81795
  userMessage.content = [
81137
- { type: "text", text: message.trim() },
81796
+ { type: "text", text: textContent },
81138
81797
  ...images.map((image) => ({
81139
81798
  type: "image",
81140
81799
  image
@@ -81216,44 +81875,83 @@ You are working with a repository located at: ${searchDirectory}
81216
81875
  }
81217
81876
  }
81218
81877
  let assistantResponseContent = "";
81219
- try {
81220
- const executeAIRequest = async () => {
81221
- const messagesForAI = this.prepareMessagesWithImages(currentMessages);
81222
- const result = await this.streamTextWithRetryAndFallback({
81223
- model: this.provider(this.model),
81224
- messages: messagesForAI,
81225
- maxTokens: maxResponseTokens,
81226
- temperature: 0.3
81227
- });
81228
- const usagePromise = result.usage;
81229
- for await (const delta of result.textStream) {
81230
- assistantResponseContent += delta;
81231
- if (options.onStream) {
81232
- options.onStream(delta);
81878
+ let compactionAttempted = false;
81879
+ while (true) {
81880
+ try {
81881
+ const executeAIRequest = async () => {
81882
+ const messagesForAI = this.prepareMessagesWithImages(currentMessages);
81883
+ const result = await this.streamTextWithRetryAndFallback({
81884
+ model: this.provider(this.model),
81885
+ messages: messagesForAI,
81886
+ maxTokens: maxResponseTokens,
81887
+ temperature: 0.3
81888
+ });
81889
+ const usagePromise = result.usage;
81890
+ for await (const delta of result.textStream) {
81891
+ assistantResponseContent += delta;
81892
+ if (options.onStream) {
81893
+ options.onStream(delta);
81894
+ }
81895
+ }
81896
+ const usage = await usagePromise;
81897
+ if (usage) {
81898
+ this.tokenCounter.recordUsage(usage, result.experimental_providerMetadata);
81233
81899
  }
81900
+ return result;
81901
+ };
81902
+ if (this.tracer) {
81903
+ await this.tracer.withSpan("ai.request", executeAIRequest, {
81904
+ "ai.model": this.model,
81905
+ "ai.provider": this.clientApiProvider || "auto",
81906
+ "iteration": currentIteration,
81907
+ "max_tokens": maxResponseTokens,
81908
+ "temperature": 0.3,
81909
+ "message_count": currentMessages.length
81910
+ });
81911
+ } else {
81912
+ await executeAIRequest();
81234
81913
  }
81235
- const usage = await usagePromise;
81236
- if (usage) {
81237
- this.tokenCounter.recordUsage(usage, result.experimental_providerMetadata);
81914
+ break;
81915
+ } catch (error2) {
81916
+ if (!compactionAttempted && handleContextLimitError) {
81917
+ const compactionResult = handleContextLimitError(error2, currentMessages, {
81918
+ keepLastSegment: true,
81919
+ minSegmentsToKeep: 1
81920
+ });
81921
+ if (compactionResult) {
81922
+ const { messages: compactedMessages, stats } = compactionResult;
81923
+ if (stats.removed === 0) {
81924
+ console.error(`[ERROR] Context window exceeded but no messages can be compacted.`);
81925
+ console.error(`[ERROR] The conversation history is already minimal (${stats.originalCount} messages).`);
81926
+ finalResult = `Error: Context window limit exceeded and conversation cannot be compacted further. Consider starting a new session or reducing system message size.`;
81927
+ throw new Error(finalResult);
81928
+ }
81929
+ compactionAttempted = true;
81930
+ console.log(`[INFO] Context window limit exceeded. Compacting conversation...`);
81931
+ console.log(`[INFO] Removed ${stats.removed} messages (${stats.reductionPercent}% reduction)`);
81932
+ console.log(`[INFO] Estimated token savings: ${stats.tokensSaved} tokens`);
81933
+ if (this.debug) {
81934
+ console.log(`[DEBUG] Compaction stats:`, stats);
81935
+ console.log(`[DEBUG] Original message count: ${stats.originalCount}`);
81936
+ console.log(`[DEBUG] Compacted message count: ${stats.compactedCount}`);
81937
+ }
81938
+ currentMessages = [...compactedMessages];
81939
+ if (this.tracer) {
81940
+ this.tracer.addEvent("context.compacted", {
81941
+ "iteration": currentIteration,
81942
+ "original_count": stats.originalCount,
81943
+ "compacted_count": stats.compactedCount,
81944
+ "reduction_percent": stats.reductionPercent,
81945
+ "tokens_saved": stats.tokensSaved
81946
+ });
81947
+ }
81948
+ continue;
81949
+ }
81238
81950
  }
81239
- return result;
81240
- };
81241
- if (this.tracer) {
81242
- await this.tracer.withSpan("ai.request", executeAIRequest, {
81243
- "ai.model": this.model,
81244
- "ai.provider": this.clientApiProvider || "auto",
81245
- "iteration": currentIteration,
81246
- "max_tokens": maxResponseTokens,
81247
- "temperature": 0.3,
81248
- "message_count": currentMessages.length
81249
- });
81250
- } else {
81251
- await executeAIRequest();
81951
+ console.error(`Error during streamText (Iter ${currentIteration}):`, error2);
81952
+ finalResult = `Error: Failed to get response from AI model during iteration ${currentIteration}. ${error2.message}`;
81953
+ throw new Error(finalResult);
81252
81954
  }
81253
- } catch (error2) {
81254
- console.error(`Error during streamText (Iter ${currentIteration}):`, error2);
81255
- finalResult = `Error: Failed to get response from AI model during iteration ${currentIteration}. ${error2.message}`;
81256
- throw new Error(finalResult);
81257
81955
  }
81258
81956
  if (this.debug && assistantResponseContent) {
81259
81957
  const assistantPreview = createMessagePreview(assistantResponseContent);
@@ -81524,15 +82222,7 @@ Remember: Use proper XML format with BOTH opening and closing tags:
81524
82222
  <tool_name>
81525
82223
  <parameter>value</parameter>
81526
82224
  </tool_name>
81527
-
81528
- IMPORTANT: A schema was provided for the final output format.
81529
-
81530
- You MUST use attempt_completion to provide your answer:
81531
- <attempt_completion>
81532
- [Your complete answer here - provide in natural language, it will be automatically formatted to match the schema]
81533
- </attempt_completion>
81534
-
81535
- Your response will be automatically formatted to JSON. You can provide your answer in natural language or as JSON - either will work.`;
82225
+ ` + generateSchemaInstructions(options.schema, { debug: this.debug }).trim();
81536
82226
  } else {
81537
82227
  reminderContent = `Please use one of the available tools to help answer the question, or use attempt_completion if you have enough information to provide a final answer.
81538
82228
 
@@ -81618,7 +82308,6 @@ Convert your previous response content into actual JSON data that follows this s
81618
82308
  ...options,
81619
82309
  _schemaFormatted: true
81620
82310
  });
81621
- finalResult = cleanSchemaResponse(finalResult);
81622
82311
  if (!this.disableMermaidValidation) {
81623
82312
  try {
81624
82313
  if (this.debug) {
@@ -81674,14 +82363,11 @@ Convert your previous response content into actual JSON data that follows this s
81674
82363
  } else if (this.debug) {
81675
82364
  console.log(`[DEBUG] Mermaid validation: Skipped due to disableMermaidValidation option`);
81676
82365
  }
82366
+ finalResult = cleanSchemaResponse(finalResult);
81677
82367
  if (isJsonSchema(options.schema)) {
81678
82368
  if (this.debug) {
81679
82369
  console.log(`[DEBUG] JSON validation: Starting validation process for schema response`);
81680
- console.log(`[DEBUG] JSON validation: Response length: ${finalResult.length} chars`);
81681
- }
81682
- finalResult = cleanSchemaResponse(finalResult);
81683
- if (this.debug) {
81684
- console.log(`[DEBUG] JSON validation: After cleaning, length: ${finalResult.length} chars`);
82370
+ console.log(`[DEBUG] JSON validation: Cleaned response length: ${finalResult.length} chars`);
81685
82371
  }
81686
82372
  if (this.tracer) {
81687
82373
  this.tracer.recordJsonValidationEvent("started", {
@@ -81771,10 +82457,9 @@ Convert your previous response content into actual JSON data that follows this s
81771
82457
  console.log("[DEBUG] Skipping schema formatting due to max iterations reached without completion");
81772
82458
  } else if (completionAttempted && options.schema && !options._schemaFormatted && !options._skipValidation) {
81773
82459
  try {
81774
- finalResult = cleanSchemaResponse(finalResult);
81775
82460
  if (!this.disableMermaidValidation) {
81776
82461
  if (this.debug) {
81777
- console.log(`[DEBUG] Mermaid validation: Validating attempt_completion result...`);
82462
+ console.log(`[DEBUG] Mermaid validation: Validating attempt_completion result BEFORE schema cleaning...`);
81778
82463
  }
81779
82464
  const mermaidValidation = await validateAndFixMermaidResponse(finalResult, {
81780
82465
  debug: this.debug,
@@ -81797,6 +82482,7 @@ Convert your previous response content into actual JSON data that follows this s
81797
82482
  } else if (this.debug) {
81798
82483
  console.log(`[DEBUG] Mermaid validation: Skipped for attempt_completion result due to disableMermaidValidation option`);
81799
82484
  }
82485
+ finalResult = cleanSchemaResponse(finalResult);
81800
82486
  if (isJsonSchema(options.schema)) {
81801
82487
  if (this.debug) {
81802
82488
  console.log(`[DEBUG] JSON validation: Starting validation process for attempt_completion result`);
@@ -81970,6 +82656,56 @@ Convert your previous response content into actual JSON data that follows this s
81970
82656
  console.log(`[DEBUG] Cleared conversation history and reset counters for session ${this.sessionId}`);
81971
82657
  }
81972
82658
  }
82659
+ /**
82660
+ * Manually compact conversation history
82661
+ * Removes intermediate monologues from older segments while preserving
82662
+ * user messages, final answers, and the most recent segment
82663
+ *
82664
+ * @param {Object} options - Compaction options
82665
+ * @param {boolean} [options.keepLastSegment=true] - Keep the most recent segment intact
82666
+ * @param {number} [options.minSegmentsToKeep=1] - Number of recent segments to preserve fully
82667
+ * @returns {Object} Compaction statistics
82668
+ */
82669
+ async compactHistory(options = {}) {
82670
+ const { compactMessages: compactMessages2, calculateCompactionStats: calculateCompactionStats2 } = await Promise.resolve().then(() => (init_contextCompactor(), contextCompactor_exports));
82671
+ if (this.history.length === 0) {
82672
+ if (this.debug) {
82673
+ console.log(`[DEBUG] No history to compact for session ${this.sessionId}`);
82674
+ }
82675
+ return {
82676
+ originalCount: 0,
82677
+ compactedCount: 0,
82678
+ removed: 0,
82679
+ reductionPercent: 0,
82680
+ originalTokens: 0,
82681
+ compactedTokens: 0,
82682
+ tokensSaved: 0
82683
+ };
82684
+ }
82685
+ const compactedMessages = compactMessages2(this.history, options);
82686
+ const stats = calculateCompactionStats2(this.history, compactedMessages);
82687
+ this.history = compactedMessages;
82688
+ try {
82689
+ await this.storageAdapter.clearHistory(this.sessionId);
82690
+ for (const message of compactedMessages) {
82691
+ await this.storageAdapter.saveMessage(this.sessionId, message);
82692
+ }
82693
+ } catch (error2) {
82694
+ console.error(`[ERROR] Failed to save compacted messages to storage:`, error2);
82695
+ }
82696
+ console.log(`[INFO] Manually compacted conversation history`);
82697
+ console.log(`[INFO] Removed ${stats.removed} messages (${stats.reductionPercent}% reduction)`);
82698
+ console.log(`[INFO] Estimated token savings: ${stats.tokensSaved} tokens`);
82699
+ if (this.debug) {
82700
+ console.log(`[DEBUG] Compaction stats:`, stats);
82701
+ }
82702
+ await this.hooks.emit(HOOK_TYPES.STORAGE_SAVE, {
82703
+ sessionId: this.sessionId,
82704
+ compacted: true,
82705
+ stats
82706
+ });
82707
+ return stats;
82708
+ }
81973
82709
  /**
81974
82710
  * Clone this agent's session to create a new agent with shared conversation history
81975
82711
  * @param {Object} options - Clone options
@@ -81992,6 +82728,14 @@ Convert your previous response content into actual JSON data that follows this s
81992
82728
  if (stripInternalMessages) {
81993
82729
  clonedHistory = this._stripInternalMessages(clonedHistory, keepSystemMessage);
81994
82730
  }
82731
+ let allowedToolsArray = null;
82732
+ if (this.allowedTools.mode === "whitelist") {
82733
+ allowedToolsArray = [...this.allowedTools.allowed];
82734
+ } else if (this.allowedTools.mode === "none") {
82735
+ allowedToolsArray = [];
82736
+ } else if (this.allowedTools.mode === "all" && this.allowedTools.exclusions.length > 0) {
82737
+ allowedToolsArray = ["*", ...this.allowedTools.exclusions.map((t3) => "!" + t3)];
82738
+ }
81995
82739
  const clonedAgent = new _ProbeAgent({
81996
82740
  // Copy current agent's config
81997
82741
  customPrompt: this.customPrompt,
@@ -82009,6 +82753,7 @@ Convert your previous response content into actual JSON data that follows this s
82009
82753
  maxIterations: this.maxIterations,
82010
82754
  disableMermaidValidation: this.disableMermaidValidation,
82011
82755
  disableJsonValidation: this.disableJsonValidation,
82756
+ allowedTools: allowedToolsArray,
82012
82757
  enableMcp: !!this.mcpBridge,
82013
82758
  mcpConfig: this.mcpConfig,
82014
82759
  enableBash: this.enableBash,