@caupulican/pi-ai 0.81.11 → 0.81.13

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.
Files changed (77) hide show
  1. package/dist/api-registry.d.ts.map +1 -1
  2. package/dist/api-registry.js +17 -1
  3. package/dist/api-registry.js.map +1 -1
  4. package/dist/env-api-keys.d.ts.map +1 -1
  5. package/dist/env-api-keys.js +27 -16
  6. package/dist/env-api-keys.js.map +1 -1
  7. package/dist/index.d.ts +3 -0
  8. package/dist/index.d.ts.map +1 -1
  9. package/dist/index.js +3 -0
  10. package/dist/index.js.map +1 -1
  11. package/dist/models.generated.d.ts +120 -0
  12. package/dist/models.generated.d.ts.map +1 -1
  13. package/dist/models.generated.js +124 -4
  14. package/dist/models.generated.js.map +1 -1
  15. package/dist/providers/amazon-bedrock.d.ts.map +1 -1
  16. package/dist/providers/amazon-bedrock.js +39 -6
  17. package/dist/providers/amazon-bedrock.js.map +1 -1
  18. package/dist/providers/google-shared.d.ts +13 -4
  19. package/dist/providers/google-shared.d.ts.map +1 -1
  20. package/dist/providers/google-shared.js +132 -11
  21. package/dist/providers/google-shared.js.map +1 -1
  22. package/dist/providers/google-vertex.d.ts.map +1 -1
  23. package/dist/providers/google-vertex.js +16 -98
  24. package/dist/providers/google-vertex.js.map +1 -1
  25. package/dist/providers/google.d.ts.map +1 -1
  26. package/dist/providers/google.js +16 -116
  27. package/dist/providers/google.js.map +1 -1
  28. package/dist/providers/openai-completions.d.ts +2 -1
  29. package/dist/providers/openai-completions.d.ts.map +1 -1
  30. package/dist/providers/openai-completions.js +56 -22
  31. package/dist/providers/openai-completions.js.map +1 -1
  32. package/dist/providers/openai-responses-shared.d.ts.map +1 -1
  33. package/dist/providers/openai-responses-shared.js +34 -15
  34. package/dist/providers/openai-responses-shared.js.map +1 -1
  35. package/dist/providers/transform-messages.d.ts.map +1 -1
  36. package/dist/providers/transform-messages.js +25 -6
  37. package/dist/providers/transform-messages.js.map +1 -1
  38. package/dist/stream.d.ts +2 -1
  39. package/dist/stream.d.ts.map +1 -1
  40. package/dist/stream.js +79 -2
  41. package/dist/stream.js.map +1 -1
  42. package/dist/types.d.ts +29 -0
  43. package/dist/types.d.ts.map +1 -1
  44. package/dist/types.js.map +1 -1
  45. package/dist/utils/json-parse.d.ts +5 -0
  46. package/dist/utils/json-parse.d.ts.map +1 -1
  47. package/dist/utils/json-parse.js +9 -13
  48. package/dist/utils/json-parse.js.map +1 -1
  49. package/dist/utils/tool-names.d.ts +7 -0
  50. package/dist/utils/tool-names.d.ts.map +1 -0
  51. package/dist/utils/tool-names.js +46 -0
  52. package/dist/utils/tool-names.js.map +1 -0
  53. package/dist/utils/tool-repair/analyzer.d.ts +45 -0
  54. package/dist/utils/tool-repair/analyzer.d.ts.map +1 -0
  55. package/dist/utils/tool-repair/analyzer.js +255 -0
  56. package/dist/utils/tool-repair/analyzer.js.map +1 -0
  57. package/dist/utils/tool-repair/registry.d.ts +32 -0
  58. package/dist/utils/tool-repair/registry.d.ts.map +1 -0
  59. package/dist/utils/tool-repair/registry.js +129 -0
  60. package/dist/utils/tool-repair/registry.js.map +1 -0
  61. package/dist/utils/tool-repair/repairer.d.ts +16 -0
  62. package/dist/utils/tool-repair/repairer.d.ts.map +1 -0
  63. package/dist/utils/tool-repair/repairer.js +254 -0
  64. package/dist/utils/tool-repair/repairer.js.map +1 -0
  65. package/dist/utils/tool-repair/replay.d.ts +35 -0
  66. package/dist/utils/tool-repair/replay.d.ts.map +1 -0
  67. package/dist/utils/tool-repair/replay.js +200 -0
  68. package/dist/utils/tool-repair/replay.js.map +1 -0
  69. package/dist/utils/tool-repair/text-protocol.d.ts +16 -0
  70. package/dist/utils/tool-repair/text-protocol.d.ts.map +1 -0
  71. package/dist/utils/tool-repair/text-protocol.js +198 -0
  72. package/dist/utils/tool-repair/text-protocol.js.map +1 -0
  73. package/dist/utils/validation.d.ts +47 -4
  74. package/dist/utils/validation.d.ts.map +1 -1
  75. package/dist/utils/validation.js +300 -217
  76. package/dist/utils/validation.js.map +1 -1
  77. package/package.json +1 -1
@@ -1 +1 @@
1
- {"version":3,"file":"json-parse.js","sourceRoot":"","sources":["../../src/utils/json-parse.ts"],"names":[],"mappings":"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","sourcesContent":["import { parse as partialParse } from \"partial-json\";\n\nconst VALID_JSON_ESCAPES = new Set(['\"', \"\\\\\", \"/\", \"b\", \"f\", \"n\", \"r\", \"t\", \"u\"]);\n\nfunction isControlCharacter(char: string): boolean {\n\tconst codePoint = char.codePointAt(0);\n\treturn codePoint !== undefined && codePoint >= 0x00 && codePoint <= 0x1f;\n}\n\nfunction escapeControlCharacter(char: string): string {\n\tswitch (char) {\n\t\tcase \"\\b\":\n\t\t\treturn \"\\\\b\";\n\t\tcase \"\\f\":\n\t\t\treturn \"\\\\f\";\n\t\tcase \"\\n\":\n\t\t\treturn \"\\\\n\";\n\t\tcase \"\\r\":\n\t\t\treturn \"\\\\r\";\n\t\tcase \"\\t\":\n\t\t\treturn \"\\\\t\";\n\t\tdefault:\n\t\t\treturn `\\\\u${char.codePointAt(0)?.toString(16).padStart(4, \"0\") ?? \"0000\"}`;\n\t}\n}\n\n/**\n * Repairs malformed JSON string literals by:\n * - escaping raw control characters inside strings\n * - doubling backslashes before invalid escape characters\n */\nexport function repairJson(json: string): string {\n\tlet repaired = \"\";\n\tlet inString = false;\n\n\tfor (let index = 0; index < json.length; index++) {\n\t\tconst char = json[index];\n\n\t\tif (!inString) {\n\t\t\trepaired += char;\n\t\t\tif (char === '\"') {\n\t\t\t\tinString = true;\n\t\t\t}\n\t\t\tcontinue;\n\t\t}\n\n\t\tif (char === '\"') {\n\t\t\trepaired += char;\n\t\t\tinString = false;\n\t\t\tcontinue;\n\t\t}\n\n\t\tif (char === \"\\\\\") {\n\t\t\tconst nextChar = json[index + 1];\n\t\t\tif (nextChar === undefined) {\n\t\t\t\trepaired += \"\\\\\\\\\";\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tif (nextChar === \"u\") {\n\t\t\t\tconst unicodeDigits = json.slice(index + 2, index + 6);\n\t\t\t\tif (/^[0-9a-fA-F]{4}$/.test(unicodeDigits)) {\n\t\t\t\t\trepaired += `\\\\u${unicodeDigits}`;\n\t\t\t\t\tindex += 5;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\trepaired += \"\\\\\\\\\";\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tif (VALID_JSON_ESCAPES.has(nextChar)) {\n\t\t\t\trepaired += `\\\\${nextChar}`;\n\t\t\t\tindex += 1;\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\trepaired += \"\\\\\\\\\";\n\t\t\tcontinue;\n\t\t}\n\n\t\trepaired += isControlCharacter(char) ? escapeControlCharacter(char) : char;\n\t}\n\n\treturn repaired;\n}\n\nexport function parseJsonWithRepair<T>(json: string): T {\n\ttry {\n\t\treturn JSON.parse(json) as T;\n\t} catch (error) {\n\t\tconst repairedJson = repairJson(json);\n\t\tif (repairedJson !== json) {\n\t\t\treturn JSON.parse(repairedJson) as T;\n\t\t}\n\t\tthrow error;\n\t}\n}\n\n/**\n * Attempts to parse potentially incomplete JSON during streaming.\n * Always returns a valid object, even if the JSON is incomplete.\n *\n * @param partialJson The partial JSON string from streaming\n * @returns Parsed object or empty object if parsing fails\n */\nexport function parseStreamingJson<T = Record<string, unknown>>(partialJson: string | undefined): T {\n\tif (!partialJson || partialJson.trim() === \"\") {\n\t\treturn {} as T;\n\t}\n\n\ttry {\n\t\treturn parseJsonWithRepair<T>(partialJson);\n\t} catch {\n\t\ttry {\n\t\t\tconst result = partialParse(partialJson);\n\t\t\treturn (result ?? {}) as T;\n\t\t} catch {\n\t\t\ttry {\n\t\t\t\tconst result = partialParse(repairJson(partialJson));\n\t\t\t\treturn (result ?? {}) as T;\n\t\t\t} catch {\n\t\t\t\treturn {} as T;\n\t\t\t}\n\t\t}\n\t}\n}\n"]}
1
+ {"version":3,"file":"json-parse.js","sourceRoot":"","sources":["../../src/utils/json-parse.ts"],"names":[],"mappings":"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","sourcesContent":["import { parse as partialParse } from \"partial-json\";\n\nconst VALID_JSON_ESCAPES = new Set(['\"', \"\\\\\", \"/\", \"b\", \"f\", \"n\", \"r\", \"t\", \"u\"]);\n\nfunction isControlCharacter(char: string): boolean {\n\tconst codePoint = char.codePointAt(0);\n\treturn codePoint !== undefined && codePoint >= 0x00 && codePoint <= 0x1f;\n}\n\nfunction escapeControlCharacter(char: string): string {\n\tswitch (char) {\n\t\tcase \"\\b\":\n\t\t\treturn \"\\\\b\";\n\t\tcase \"\\f\":\n\t\t\treturn \"\\\\f\";\n\t\tcase \"\\n\":\n\t\t\treturn \"\\\\n\";\n\t\tcase \"\\r\":\n\t\t\treturn \"\\\\r\";\n\t\tcase \"\\t\":\n\t\t\treturn \"\\\\t\";\n\t\tdefault:\n\t\t\treturn `\\\\u${char.codePointAt(0)?.toString(16).padStart(4, \"0\") ?? \"0000\"}`;\n\t}\n}\n\n/**\n * Repairs malformed JSON string literals by:\n * - escaping raw control characters inside strings\n * - doubling backslashes before invalid escape characters\n */\nexport function repairJson(json: string): string {\n\tlet repaired = \"\";\n\tlet inString = false;\n\n\tfor (let index = 0; index < json.length; index++) {\n\t\tconst char = json[index];\n\n\t\tif (!inString) {\n\t\t\trepaired += char;\n\t\t\tif (char === '\"') {\n\t\t\t\tinString = true;\n\t\t\t}\n\t\t\tcontinue;\n\t\t}\n\n\t\tif (char === '\"') {\n\t\t\trepaired += char;\n\t\t\tinString = false;\n\t\t\tcontinue;\n\t\t}\n\n\t\tif (char === \"\\\\\") {\n\t\t\tconst nextChar = json[index + 1];\n\t\t\tif (nextChar === undefined) {\n\t\t\t\trepaired += \"\\\\\\\\\";\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tif (nextChar === \"u\") {\n\t\t\t\tconst unicodeDigits = json.slice(index + 2, index + 6);\n\t\t\t\tif (/^[0-9a-fA-F]{4}$/.test(unicodeDigits)) {\n\t\t\t\t\trepaired += `\\\\u${unicodeDigits}`;\n\t\t\t\t\tindex += 5;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\trepaired += \"\\\\\\\\\";\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tif (VALID_JSON_ESCAPES.has(nextChar)) {\n\t\t\t\trepaired += `\\\\${nextChar}`;\n\t\t\t\tindex += 1;\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\trepaired += \"\\\\\\\\\";\n\t\t\tcontinue;\n\t\t}\n\n\t\trepaired += isControlCharacter(char) ? escapeControlCharacter(char) : char;\n\t}\n\n\treturn repaired;\n}\n\nexport function parseJsonWithRepair<T>(json: string): T {\n\ttry {\n\t\treturn JSON.parse(json) as T;\n\t} catch (error) {\n\t\tconst repairedJson = repairJson(json);\n\t\tif (repairedJson !== json) {\n\t\t\treturn JSON.parse(repairedJson) as T;\n\t\t}\n\t\tthrow error;\n\t}\n}\n\n/**\n * Attempts to parse potentially incomplete JSON during streaming.\n * Always returns a valid object, even if the JSON is incomplete.\n *\n * @param partialJson The partial JSON string from streaming\n * @returns Parsed object or empty object if parsing fails\n */\nexport interface StreamingJsonParseResult<T> {\n\tcomplete: boolean;\n\tvalue: T;\n}\n\nexport function parseStreamingJsonState<T = Record<string, unknown>>(\n\tpartialJson: string | undefined,\n): StreamingJsonParseResult<T> {\n\tif (!partialJson || partialJson.trim() === \"\") {\n\t\treturn { complete: true, value: {} as T };\n\t}\n\n\ttry {\n\t\treturn { complete: true, value: parseJsonWithRepair<T>(partialJson) };\n\t} catch {\n\t\ttry {\n\t\t\tconst result = partialParse(partialJson);\n\t\t\treturn { complete: false, value: (result ?? {}) as T };\n\t\t} catch {\n\t\t\ttry {\n\t\t\t\tconst result = partialParse(repairJson(partialJson));\n\t\t\t\treturn { complete: false, value: (result ?? {}) as T };\n\t\t\t} catch {\n\t\t\t\treturn { complete: false, value: {} as T };\n\t\t\t}\n\t\t}\n\t}\n}\n\nexport function parseStreamingJson<T = Record<string, unknown>>(partialJson: string | undefined): T {\n\treturn parseStreamingJsonState<T>(partialJson).value;\n}\n"]}
@@ -0,0 +1,7 @@
1
+ import type { Tool } from "../types.ts";
2
+ export interface ToolNameMap {
3
+ toProviderName(name: string): string;
4
+ toOriginalName(name: string): string;
5
+ }
6
+ export declare function createToolNameMap(tools: readonly Tool[]): ToolNameMap;
7
+ //# sourceMappingURL=tool-names.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tool-names.d.ts","sourceRoot":"","sources":["../../src/utils/tool-names.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,aAAa,CAAC;AAKxC,MAAM,WAAW,WAAW;IAC3B,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAAC;IACrC,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAAC;CACrC;AA6BD,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,SAAS,IAAI,EAAE,GAAG,WAAW,CAoBrE","sourcesContent":["import type { Tool } from \"../types.ts\";\n\nconst VALID_TOOL_NAME = /^[a-zA-Z0-9_-]{1,64}$/;\nconst MAX_TOOL_NAME_LENGTH = 64;\n\nexport interface ToolNameMap {\n\ttoProviderName(name: string): string;\n\ttoOriginalName(name: string): string;\n}\n\nfunction baseSanitizedToolName(name: string): string {\n\tconst sanitized = name\n\t\t.replace(/[^a-zA-Z0-9_-]/g, \"_\")\n\t\t.replace(/^_+|_+$/g, \"\")\n\t\t.slice(0, MAX_TOOL_NAME_LENGTH);\n\treturn sanitized.length > 0 ? sanitized : \"tool\";\n}\n\nfunction uniqueToolName(base: string, usedNames: Set<string>): string {\n\tif (!usedNames.has(base)) {\n\t\tusedNames.add(base);\n\t\treturn base;\n\t}\n\n\tlet index = 2;\n\twhile (true) {\n\t\tconst suffix = `_${index}`;\n\t\tconst prefix = base.slice(0, MAX_TOOL_NAME_LENGTH - suffix.length);\n\t\tconst candidate = `${prefix}${suffix}`;\n\t\tif (!usedNames.has(candidate)) {\n\t\t\tusedNames.add(candidate);\n\t\t\treturn candidate;\n\t\t}\n\t\tindex++;\n\t}\n}\n\nexport function createToolNameMap(tools: readonly Tool[]): ToolNameMap {\n\tconst originalToProvider = new Map<string, string>();\n\tconst providerToOriginal = new Map<string, string>();\n\tconst usedProviderNames = new Set<string>();\n\n\tfor (const tool of tools) {\n\t\tconst base = VALID_TOOL_NAME.test(tool.name) ? tool.name : baseSanitizedToolName(tool.name);\n\t\tconst providerName = uniqueToolName(base, usedProviderNames);\n\t\toriginalToProvider.set(tool.name, providerName);\n\t\tproviderToOriginal.set(providerName, tool.name);\n\t}\n\n\treturn {\n\t\ttoProviderName(name: string): string {\n\t\t\treturn originalToProvider.get(name) ?? name;\n\t\t},\n\t\ttoOriginalName(name: string): string {\n\t\t\treturn providerToOriginal.get(name) ?? name;\n\t\t},\n\t};\n}\n"]}
@@ -0,0 +1,46 @@
1
+ const VALID_TOOL_NAME = /^[a-zA-Z0-9_-]{1,64}$/;
2
+ const MAX_TOOL_NAME_LENGTH = 64;
3
+ function baseSanitizedToolName(name) {
4
+ const sanitized = name
5
+ .replace(/[^a-zA-Z0-9_-]/g, "_")
6
+ .replace(/^_+|_+$/g, "")
7
+ .slice(0, MAX_TOOL_NAME_LENGTH);
8
+ return sanitized.length > 0 ? sanitized : "tool";
9
+ }
10
+ function uniqueToolName(base, usedNames) {
11
+ if (!usedNames.has(base)) {
12
+ usedNames.add(base);
13
+ return base;
14
+ }
15
+ let index = 2;
16
+ while (true) {
17
+ const suffix = `_${index}`;
18
+ const prefix = base.slice(0, MAX_TOOL_NAME_LENGTH - suffix.length);
19
+ const candidate = `${prefix}${suffix}`;
20
+ if (!usedNames.has(candidate)) {
21
+ usedNames.add(candidate);
22
+ return candidate;
23
+ }
24
+ index++;
25
+ }
26
+ }
27
+ export function createToolNameMap(tools) {
28
+ const originalToProvider = new Map();
29
+ const providerToOriginal = new Map();
30
+ const usedProviderNames = new Set();
31
+ for (const tool of tools) {
32
+ const base = VALID_TOOL_NAME.test(tool.name) ? tool.name : baseSanitizedToolName(tool.name);
33
+ const providerName = uniqueToolName(base, usedProviderNames);
34
+ originalToProvider.set(tool.name, providerName);
35
+ providerToOriginal.set(providerName, tool.name);
36
+ }
37
+ return {
38
+ toProviderName(name) {
39
+ return originalToProvider.get(name) ?? name;
40
+ },
41
+ toOriginalName(name) {
42
+ return providerToOriginal.get(name) ?? name;
43
+ },
44
+ };
45
+ }
46
+ //# sourceMappingURL=tool-names.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tool-names.js","sourceRoot":"","sources":["../../src/utils/tool-names.ts"],"names":[],"mappings":"AAEA,MAAM,eAAe,GAAG,uBAAuB,CAAC;AAChD,MAAM,oBAAoB,GAAG,EAAE,CAAC;AAOhC,SAAS,qBAAqB,CAAC,IAAY,EAAU;IACpD,MAAM,SAAS,GAAG,IAAI;SACpB,OAAO,CAAC,iBAAiB,EAAE,GAAG,CAAC;SAC/B,OAAO,CAAC,UAAU,EAAE,EAAE,CAAC;SACvB,KAAK,CAAC,CAAC,EAAE,oBAAoB,CAAC,CAAC;IACjC,OAAO,SAAS,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC;AAAA,CACjD;AAED,SAAS,cAAc,CAAC,IAAY,EAAE,SAAsB,EAAU;IACrE,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC;QAC1B,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;QACpB,OAAO,IAAI,CAAC;IACb,CAAC;IAED,IAAI,KAAK,GAAG,CAAC,CAAC;IACd,OAAO,IAAI,EAAE,CAAC;QACb,MAAM,MAAM,GAAG,IAAI,KAAK,EAAE,CAAC;QAC3B,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,oBAAoB,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC;QACnE,MAAM,SAAS,GAAG,GAAG,MAAM,GAAG,MAAM,EAAE,CAAC;QACvC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,SAAS,CAAC,EAAE,CAAC;YAC/B,SAAS,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC;YACzB,OAAO,SAAS,CAAC;QAClB,CAAC;QACD,KAAK,EAAE,CAAC;IACT,CAAC;AAAA,CACD;AAED,MAAM,UAAU,iBAAiB,CAAC,KAAsB,EAAe;IACtE,MAAM,kBAAkB,GAAG,IAAI,GAAG,EAAkB,CAAC;IACrD,MAAM,kBAAkB,GAAG,IAAI,GAAG,EAAkB,CAAC;IACrD,MAAM,iBAAiB,GAAG,IAAI,GAAG,EAAU,CAAC;IAE5C,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QAC1B,MAAM,IAAI,GAAG,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,qBAAqB,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC5F,MAAM,YAAY,GAAG,cAAc,CAAC,IAAI,EAAE,iBAAiB,CAAC,CAAC;QAC7D,kBAAkB,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,EAAE,YAAY,CAAC,CAAC;QAChD,kBAAkB,CAAC,GAAG,CAAC,YAAY,EAAE,IAAI,CAAC,IAAI,CAAC,CAAC;IACjD,CAAC;IAED,OAAO;QACN,cAAc,CAAC,IAAY,EAAU;YACpC,OAAO,kBAAkB,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC;QAAA,CAC5C;QACD,cAAc,CAAC,IAAY,EAAU;YACpC,OAAO,kBAAkB,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC;QAAA,CAC5C;KACD,CAAC;AAAA,CACF","sourcesContent":["import type { Tool } from \"../types.ts\";\n\nconst VALID_TOOL_NAME = /^[a-zA-Z0-9_-]{1,64}$/;\nconst MAX_TOOL_NAME_LENGTH = 64;\n\nexport interface ToolNameMap {\n\ttoProviderName(name: string): string;\n\ttoOriginalName(name: string): string;\n}\n\nfunction baseSanitizedToolName(name: string): string {\n\tconst sanitized = name\n\t\t.replace(/[^a-zA-Z0-9_-]/g, \"_\")\n\t\t.replace(/^_+|_+$/g, \"\")\n\t\t.slice(0, MAX_TOOL_NAME_LENGTH);\n\treturn sanitized.length > 0 ? sanitized : \"tool\";\n}\n\nfunction uniqueToolName(base: string, usedNames: Set<string>): string {\n\tif (!usedNames.has(base)) {\n\t\tusedNames.add(base);\n\t\treturn base;\n\t}\n\n\tlet index = 2;\n\twhile (true) {\n\t\tconst suffix = `_${index}`;\n\t\tconst prefix = base.slice(0, MAX_TOOL_NAME_LENGTH - suffix.length);\n\t\tconst candidate = `${prefix}${suffix}`;\n\t\tif (!usedNames.has(candidate)) {\n\t\t\tusedNames.add(candidate);\n\t\t\treturn candidate;\n\t\t}\n\t\tindex++;\n\t}\n}\n\nexport function createToolNameMap(tools: readonly Tool[]): ToolNameMap {\n\tconst originalToProvider = new Map<string, string>();\n\tconst providerToOriginal = new Map<string, string>();\n\tconst usedProviderNames = new Set<string>();\n\n\tfor (const tool of tools) {\n\t\tconst base = VALID_TOOL_NAME.test(tool.name) ? tool.name : baseSanitizedToolName(tool.name);\n\t\tconst providerName = uniqueToolName(base, usedProviderNames);\n\t\toriginalToProvider.set(tool.name, providerName);\n\t\tproviderToOriginal.set(providerName, tool.name);\n\t}\n\n\treturn {\n\t\ttoProviderName(name: string): string {\n\t\t\treturn originalToProvider.get(name) ?? name;\n\t\t},\n\t\ttoOriginalName(name: string): string {\n\t\t\treturn providerToOriginal.get(name) ?? name;\n\t\t},\n\t};\n}\n"]}
@@ -0,0 +1,45 @@
1
+ import type { Tool } from "../../types.ts";
2
+ import type { ToolRepairModeName } from "./registry.ts";
3
+ export interface JsonSchemaObject {
4
+ type?: string | string[];
5
+ properties?: Record<string, JsonSchemaObject>;
6
+ items?: JsonSchemaObject | JsonSchemaObject[];
7
+ required?: string[];
8
+ additionalProperties?: boolean | JsonSchemaObject;
9
+ allOf?: JsonSchemaObject[];
10
+ anyOf?: JsonSchemaObject[];
11
+ oneOf?: JsonSchemaObject[];
12
+ enum?: unknown[];
13
+ const?: unknown;
14
+ default?: unknown;
15
+ }
16
+ export interface ValidationErrorLike {
17
+ instancePath: string;
18
+ keyword: string;
19
+ message: string;
20
+ }
21
+ export interface ToolRepairIssue {
22
+ path: string[];
23
+ pathText: string;
24
+ value: unknown;
25
+ schema: JsonSchemaObject;
26
+ parentSchema?: JsonSchemaObject;
27
+ parentValue?: unknown;
28
+ propertyKey?: string;
29
+ required: boolean;
30
+ modes: ToolRepairModeName[];
31
+ }
32
+ export declare function isRecord(value: unknown): value is Record<string, unknown>;
33
+ export declare function isJsonSchemaObject(value: unknown): value is JsonSchemaObject;
34
+ export declare function parseInstancePath(instancePath: string): string[];
35
+ export declare function formatRepairPath(path: readonly string[]): string;
36
+ export declare function getValueAtPath(value: unknown, path: readonly string[]): unknown;
37
+ export declare function getSchemaTypes(schema: JsonSchemaObject): string[];
38
+ export declare function getEnumValues(schema: JsonSchemaObject): string[];
39
+ export declare function resolveSchemaAtPath(schema: JsonSchemaObject, path: readonly string[]): {
40
+ schema?: JsonSchemaObject;
41
+ parentSchema?: JsonSchemaObject;
42
+ propertyKey?: string;
43
+ };
44
+ export declare function analyzeToolArgumentErrors(toolName: string, schema: Tool["parameters"], args: Record<string, unknown>, errors: readonly ValidationErrorLike[]): ToolRepairIssue[];
45
+ //# sourceMappingURL=analyzer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"analyzer.d.ts","sourceRoot":"","sources":["../../../src/utils/tool-repair/analyzer.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,gBAAgB,CAAC;AAC3C,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAC;AAExD,MAAM,WAAW,gBAAgB;IAChC,IAAI,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC;IACzB,UAAU,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,gBAAgB,CAAC,CAAC;IAC9C,KAAK,CAAC,EAAE,gBAAgB,GAAG,gBAAgB,EAAE,CAAC;IAC9C,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,oBAAoB,CAAC,EAAE,OAAO,GAAG,gBAAgB,CAAC;IAClD,KAAK,CAAC,EAAE,gBAAgB,EAAE,CAAC;IAC3B,KAAK,CAAC,EAAE,gBAAgB,EAAE,CAAC;IAC3B,KAAK,CAAC,EAAE,gBAAgB,EAAE,CAAC;IAC3B,IAAI,CAAC,EAAE,OAAO,EAAE,CAAC;IACjB,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,OAAO,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,WAAW,mBAAmB;IACnC,YAAY,EAAE,MAAM,CAAC;IACrB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,eAAe;IAC/B,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,OAAO,CAAC;IACf,MAAM,EAAE,gBAAgB,CAAC;IACzB,YAAY,CAAC,EAAE,gBAAgB,CAAC;IAChC,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,QAAQ,EAAE,OAAO,CAAC;IAClB,KAAK,EAAE,kBAAkB,EAAE,CAAC;CAC5B;AAED,wBAAgB,QAAQ,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAEzE;AAED,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,gBAAgB,CAE5E;AAED,wBAAgB,iBAAiB,CAAC,YAAY,EAAE,MAAM,GAAG,MAAM,EAAE,CAOhE;AAED,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,SAAS,MAAM,EAAE,GAAG,MAAM,CAEhE;AAED,wBAAgB,cAAc,CAAC,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,SAAS,MAAM,EAAE,GAAG,OAAO,CAc/E;AAED,wBAAgB,cAAc,CAAC,MAAM,EAAE,gBAAgB,GAAG,MAAM,EAAE,CAuBjE;AAED,wBAAgB,aAAa,CAAC,MAAM,EAAE,gBAAgB,GAAG,MAAM,EAAE,CAkBhE;AAED,wBAAgB,mBAAmB,CAClC,MAAM,EAAE,gBAAgB,EACxB,IAAI,EAAE,SAAS,MAAM,EAAE,GACrB;IACF,MAAM,CAAC,EAAE,gBAAgB,CAAC;IAC1B,YAAY,CAAC,EAAE,gBAAgB,CAAC;IAChC,WAAW,CAAC,EAAE,MAAM,CAAC;CACrB,CA8BA;AA8HD,wBAAgB,yBAAyB,CACxC,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,IAAI,CAAC,YAAY,CAAC,EAC1B,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC7B,MAAM,EAAE,SAAS,mBAAmB,EAAE,GACpC,eAAe,EAAE,CAiCnB","sourcesContent":["import type { Tool } from \"../../types.ts\";\nimport type { ToolRepairModeName } from \"./registry.ts\";\n\nexport interface JsonSchemaObject {\n\ttype?: string | string[];\n\tproperties?: Record<string, JsonSchemaObject>;\n\titems?: JsonSchemaObject | JsonSchemaObject[];\n\trequired?: string[];\n\tadditionalProperties?: boolean | JsonSchemaObject;\n\tallOf?: JsonSchemaObject[];\n\tanyOf?: JsonSchemaObject[];\n\toneOf?: JsonSchemaObject[];\n\tenum?: unknown[];\n\tconst?: unknown;\n\tdefault?: unknown;\n}\n\nexport interface ValidationErrorLike {\n\tinstancePath: string;\n\tkeyword: string;\n\tmessage: string;\n}\n\nexport interface ToolRepairIssue {\n\tpath: string[];\n\tpathText: string;\n\tvalue: unknown;\n\tschema: JsonSchemaObject;\n\tparentSchema?: JsonSchemaObject;\n\tparentValue?: unknown;\n\tpropertyKey?: string;\n\trequired: boolean;\n\tmodes: ToolRepairModeName[];\n}\n\nexport function isRecord(value: unknown): value is Record<string, unknown> {\n\treturn typeof value === \"object\" && value !== null && !Array.isArray(value);\n}\n\nexport function isJsonSchemaObject(value: unknown): value is JsonSchemaObject {\n\treturn isRecord(value);\n}\n\nexport function parseInstancePath(instancePath: string): string[] {\n\tif (!instancePath) return [];\n\treturn instancePath\n\t\t.replace(/^\\//, \"\")\n\t\t.split(\"/\")\n\t\t.filter((segment) => segment.length > 0)\n\t\t.map((segment) => segment.replace(/~1/g, \"/\").replace(/~0/g, \"~\"));\n}\n\nexport function formatRepairPath(path: readonly string[]): string {\n\treturn path.length === 0 ? \"root\" : path.join(\".\");\n}\n\nexport function getValueAtPath(value: unknown, path: readonly string[]): unknown {\n\tlet cursor = value;\n\tfor (const segment of path) {\n\t\tif (Array.isArray(cursor)) {\n\t\t\tconst index = Number(segment);\n\t\t\tif (!Number.isInteger(index)) return undefined;\n\t\t\tcursor = cursor[index];\n\t\t} else if (isRecord(cursor)) {\n\t\t\tcursor = cursor[segment];\n\t\t} else {\n\t\t\treturn undefined;\n\t\t}\n\t}\n\treturn cursor;\n}\n\nexport function getSchemaTypes(schema: JsonSchemaObject): string[] {\n\tconst types = new Set<string>();\n\tconst addTypes = (candidate: JsonSchemaObject): void => {\n\t\tif (typeof candidate.type === \"string\") {\n\t\t\ttypes.add(candidate.type);\n\t\t} else if (Array.isArray(candidate.type)) {\n\t\t\tfor (const type of candidate.type) {\n\t\t\t\tif (typeof type === \"string\") types.add(type);\n\t\t\t}\n\t\t}\n\t\tif (candidate.enum?.every((value) => typeof value === \"string\")) {\n\t\t\ttypes.add(\"string\");\n\t\t}\n\t\tif (typeof candidate.const === \"string\") {\n\t\t\ttypes.add(\"string\");\n\t\t}\n\t};\n\n\taddTypes(schema);\n\tfor (const nested of [...(schema.anyOf ?? []), ...(schema.oneOf ?? []), ...(schema.allOf ?? [])]) {\n\t\taddTypes(nested);\n\t}\n\treturn [...types];\n}\n\nexport function getEnumValues(schema: JsonSchemaObject): string[] {\n\tconst values: string[] = [];\n\tconst addValues = (candidate: JsonSchemaObject): void => {\n\t\tif (Array.isArray(candidate.enum)) {\n\t\t\tfor (const value of candidate.enum) {\n\t\t\t\tif (typeof value === \"string\") values.push(value);\n\t\t\t}\n\t\t}\n\t\tif (typeof candidate.const === \"string\") {\n\t\t\tvalues.push(candidate.const);\n\t\t}\n\t};\n\n\taddValues(schema);\n\tfor (const nested of [...(schema.anyOf ?? []), ...(schema.oneOf ?? [])]) {\n\t\taddValues(nested);\n\t}\n\treturn values;\n}\n\nexport function resolveSchemaAtPath(\n\tschema: JsonSchemaObject,\n\tpath: readonly string[],\n): {\n\tschema?: JsonSchemaObject;\n\tparentSchema?: JsonSchemaObject;\n\tpropertyKey?: string;\n} {\n\tlet cursor: JsonSchemaObject | undefined = schema;\n\tlet parentSchema: JsonSchemaObject | undefined;\n\tlet propertyKey: string | undefined;\n\n\tfor (const segment of path) {\n\t\tif (!cursor) return { schema: undefined, parentSchema, propertyKey };\n\t\tparentSchema = cursor;\n\t\tpropertyKey = segment;\n\t\tif (cursor.properties?.[segment]) {\n\t\t\tcursor = cursor.properties[segment];\n\t\t\tcontinue;\n\t\t}\n\t\tif (Array.isArray(cursor.items)) {\n\t\t\tconst index = Number(segment);\n\t\t\tcursor = Number.isInteger(index) ? cursor.items[index] : undefined;\n\t\t\tcontinue;\n\t\t}\n\t\tif (isJsonSchemaObject(cursor.items)) {\n\t\t\tcursor = cursor.items;\n\t\t\tcontinue;\n\t\t}\n\t\tif (isJsonSchemaObject(cursor.additionalProperties)) {\n\t\t\tcursor = cursor.additionalProperties;\n\t\t\tcontinue;\n\t\t}\n\t\treturn { schema: undefined, parentSchema, propertyKey };\n\t}\n\n\treturn { schema: cursor, parentSchema, propertyKey };\n}\n\nfunction isRequired(parentSchema: JsonSchemaObject | undefined, propertyKey: string | undefined): boolean {\n\treturn Boolean(propertyKey && parentSchema?.required?.includes(propertyKey));\n}\n\nfunction isScalarSchema(schema: JsonSchemaObject): boolean {\n\treturn getSchemaTypes(schema).some((type) => [\"string\", \"number\", \"integer\", \"boolean\"].includes(type));\n}\n\nfunction isArraySchema(schema: JsonSchemaObject): boolean {\n\treturn getSchemaTypes(schema).includes(\"array\");\n}\n\nfunction isObjectSchema(schema: JsonSchemaObject): boolean {\n\treturn getSchemaTypes(schema).includes(\"object\");\n}\n\nfunction normalizeEnumValue(value: string): string {\n\treturn value.trim().replace(/\\s+/g, \" \").toLowerCase();\n}\n\nfunction enumNormalizeHasMatch(schema: JsonSchemaObject, value: string): boolean {\n\tconst normalized = normalizeEnumValue(value);\n\treturn getEnumValues(schema).filter((candidate) => normalizeEnumValue(candidate) === normalized).length === 1;\n}\n\nfunction isEmptyObject(value: unknown): boolean {\n\treturn isRecord(value) && Object.keys(value).length === 0;\n}\n\nfunction isScalarValue(value: unknown): boolean {\n\treturn [\"string\", \"number\", \"boolean\"].includes(typeof value);\n}\n\nfunction getParentPath(path: readonly string[]): string[] {\n\treturn path.slice(0, -1);\n}\n\nfunction isNumericArrayParentIssue(\n\targs: Record<string, unknown>,\n\trootSchema: JsonSchemaObject,\n\tpath: readonly string[],\n): ToolRepairIssue | undefined {\n\tif (path.length === 0) return undefined;\n\tconst parentPath = getParentPath(path);\n\tconst parentLookup = resolveSchemaAtPath(rootSchema, parentPath);\n\tconst parentSchema = parentLookup.schema;\n\tif (!parentSchema || !isArraySchema(parentSchema) || Array.isArray(parentSchema.items)) return undefined;\n\tif (!isJsonSchemaObject(parentSchema.items)) return undefined;\n\tconst itemTypes = getSchemaTypes(parentSchema.items);\n\tif (!itemTypes.some((type) => type === \"number\" || type === \"integer\")) return undefined;\n\tconst parentValue = getValueAtPath(args, parentPath);\n\tif (!Array.isArray(parentValue) || !parentValue.every((item) => typeof item === \"string\")) return undefined;\n\treturn {\n\t\tpath: parentPath,\n\t\tpathText: formatRepairPath(parentPath),\n\t\tvalue: parentValue,\n\t\tschema: parentSchema,\n\t\tparentSchema: parentLookup.parentSchema,\n\t\tparentValue: getValueAtPath(args, getParentPath(parentPath)),\n\t\tpropertyKey: parentLookup.propertyKey,\n\t\trequired: isRequired(parentLookup.parentSchema, parentLookup.propertyKey),\n\t\tmodes: [\"stringifiedNumberInArray\"],\n\t};\n}\n\nfunction classifyModes(toolName: string, issue: Omit<ToolRepairIssue, \"modes\">): ToolRepairModeName[] {\n\tconst modes: ToolRepairModeName[] = [];\n\tconst expectedTypes = getSchemaTypes(issue.schema);\n\n\tif (toolName === \"bash\" && issue.pathText === \"command\") {\n\t\tif (Array.isArray(issue.value) && issue.value.every((item) => typeof item === \"string\")) {\n\t\t\tmodes.push(\"bashCommandArgvJoin\");\n\t\t}\n\t\tif (isRecord(issue.value)) {\n\t\t\tmodes.push(\"bashCommandUnwrap\");\n\t\t}\n\t}\n\n\tif (typeof issue.value === \"string\" && (isArraySchema(issue.schema) || isObjectSchema(issue.schema))) {\n\t\tmodes.push(\"jsonStringParse\");\n\t}\n\tif (isArraySchema(issue.schema) && isRecord(issue.value)) {\n\t\tmodes.push(\"singleObjectWrap\", \"emptyObjectPlaceholder\");\n\t}\n\tif (isArraySchema(issue.schema) && isScalarValue(issue.value)) {\n\t\tmodes.push(\"bareScalarWrap\");\n\t}\n\tif (typeof issue.value === \"string\" && expectedTypes.some((type) => type === \"number\" || type === \"integer\")) {\n\t\tmodes.push(\"numberFromString\");\n\t}\n\tif (typeof issue.value === \"string\" && expectedTypes.includes(\"boolean\")) {\n\t\tmodes.push(\"boolFromString\");\n\t}\n\tif (typeof issue.value === \"string\" && enumNormalizeHasMatch(issue.schema, issue.value)) {\n\t\tmodes.push(\"enumCaseNormalize\");\n\t}\n\tif (Array.isArray(issue.value) && issue.value.length === 1 && isScalarSchema(issue.schema)) {\n\t\tmodes.push(\"singleElementUnwrap\");\n\t}\n\tif (!issue.required && isEmptyObject(issue.value) && isScalarSchema(issue.schema)) {\n\t\tmodes.push(\"emptyObjectPlaceholder\");\n\t}\n\tif (issue.value === null) {\n\t\tmodes.push(issue.required ? \"nullRequiredBounce\" : \"nullOptionalDrop\");\n\t}\n\n\treturn modes;\n}\n\nfunction comparePaths(a: readonly string[], b: readonly string[]): number {\n\tconst length = Math.min(a.length, b.length);\n\tfor (let index = 0; index < length; index++) {\n\t\tconst left = a[index];\n\t\tconst right = b[index];\n\t\tconst leftNumber = Number(left);\n\t\tconst rightNumber = Number(right);\n\t\tif (Number.isInteger(leftNumber) && Number.isInteger(rightNumber) && leftNumber !== rightNumber) {\n\t\t\treturn leftNumber - rightNumber;\n\t\t}\n\t\tif (left !== right) return left < right ? -1 : 1;\n\t}\n\treturn a.length - b.length;\n}\n\nexport function analyzeToolArgumentErrors(\n\ttoolName: string,\n\tschema: Tool[\"parameters\"],\n\targs: Record<string, unknown>,\n\terrors: readonly ValidationErrorLike[],\n): ToolRepairIssue[] {\n\tconst rootSchema = schema as JsonSchemaObject;\n\tconst issues = new Map<string, ToolRepairIssue>();\n\n\tfor (const error of errors) {\n\t\tif (error.keyword === \"required\") continue;\n\t\tconst path = parseInstancePath(error.instancePath);\n\t\tconst numericArrayIssue = isNumericArrayParentIssue(args, rootSchema, path);\n\t\tif (numericArrayIssue) {\n\t\t\tissues.set(numericArrayIssue.pathText, numericArrayIssue);\n\t\t\tcontinue;\n\t\t}\n\n\t\tconst lookup = resolveSchemaAtPath(rootSchema, path);\n\t\tif (!lookup.schema) continue;\n\t\tconst value = getValueAtPath(args, path);\n\t\tconst issueBase = {\n\t\t\tpath,\n\t\t\tpathText: formatRepairPath(path),\n\t\t\tvalue,\n\t\t\tschema: lookup.schema,\n\t\t\tparentSchema: lookup.parentSchema,\n\t\t\tparentValue: getValueAtPath(args, getParentPath(path)),\n\t\t\tpropertyKey: lookup.propertyKey,\n\t\t\trequired: isRequired(lookup.parentSchema, lookup.propertyKey),\n\t\t};\n\t\tconst modes = classifyModes(toolName, issueBase);\n\t\tif (modes.length > 0) {\n\t\t\tissues.set(issueBase.pathText, { ...issueBase, modes });\n\t\t}\n\t}\n\n\treturn [...issues.values()].sort((left, right) => comparePaths(left.path, right.path));\n}\n"]}
@@ -0,0 +1,255 @@
1
+ export function isRecord(value) {
2
+ return typeof value === "object" && value !== null && !Array.isArray(value);
3
+ }
4
+ export function isJsonSchemaObject(value) {
5
+ return isRecord(value);
6
+ }
7
+ export function parseInstancePath(instancePath) {
8
+ if (!instancePath)
9
+ return [];
10
+ return instancePath
11
+ .replace(/^\//, "")
12
+ .split("/")
13
+ .filter((segment) => segment.length > 0)
14
+ .map((segment) => segment.replace(/~1/g, "/").replace(/~0/g, "~"));
15
+ }
16
+ export function formatRepairPath(path) {
17
+ return path.length === 0 ? "root" : path.join(".");
18
+ }
19
+ export function getValueAtPath(value, path) {
20
+ let cursor = value;
21
+ for (const segment of path) {
22
+ if (Array.isArray(cursor)) {
23
+ const index = Number(segment);
24
+ if (!Number.isInteger(index))
25
+ return undefined;
26
+ cursor = cursor[index];
27
+ }
28
+ else if (isRecord(cursor)) {
29
+ cursor = cursor[segment];
30
+ }
31
+ else {
32
+ return undefined;
33
+ }
34
+ }
35
+ return cursor;
36
+ }
37
+ export function getSchemaTypes(schema) {
38
+ const types = new Set();
39
+ const addTypes = (candidate) => {
40
+ if (typeof candidate.type === "string") {
41
+ types.add(candidate.type);
42
+ }
43
+ else if (Array.isArray(candidate.type)) {
44
+ for (const type of candidate.type) {
45
+ if (typeof type === "string")
46
+ types.add(type);
47
+ }
48
+ }
49
+ if (candidate.enum?.every((value) => typeof value === "string")) {
50
+ types.add("string");
51
+ }
52
+ if (typeof candidate.const === "string") {
53
+ types.add("string");
54
+ }
55
+ };
56
+ addTypes(schema);
57
+ for (const nested of [...(schema.anyOf ?? []), ...(schema.oneOf ?? []), ...(schema.allOf ?? [])]) {
58
+ addTypes(nested);
59
+ }
60
+ return [...types];
61
+ }
62
+ export function getEnumValues(schema) {
63
+ const values = [];
64
+ const addValues = (candidate) => {
65
+ if (Array.isArray(candidate.enum)) {
66
+ for (const value of candidate.enum) {
67
+ if (typeof value === "string")
68
+ values.push(value);
69
+ }
70
+ }
71
+ if (typeof candidate.const === "string") {
72
+ values.push(candidate.const);
73
+ }
74
+ };
75
+ addValues(schema);
76
+ for (const nested of [...(schema.anyOf ?? []), ...(schema.oneOf ?? [])]) {
77
+ addValues(nested);
78
+ }
79
+ return values;
80
+ }
81
+ export function resolveSchemaAtPath(schema, path) {
82
+ let cursor = schema;
83
+ let parentSchema;
84
+ let propertyKey;
85
+ for (const segment of path) {
86
+ if (!cursor)
87
+ return { schema: undefined, parentSchema, propertyKey };
88
+ parentSchema = cursor;
89
+ propertyKey = segment;
90
+ if (cursor.properties?.[segment]) {
91
+ cursor = cursor.properties[segment];
92
+ continue;
93
+ }
94
+ if (Array.isArray(cursor.items)) {
95
+ const index = Number(segment);
96
+ cursor = Number.isInteger(index) ? cursor.items[index] : undefined;
97
+ continue;
98
+ }
99
+ if (isJsonSchemaObject(cursor.items)) {
100
+ cursor = cursor.items;
101
+ continue;
102
+ }
103
+ if (isJsonSchemaObject(cursor.additionalProperties)) {
104
+ cursor = cursor.additionalProperties;
105
+ continue;
106
+ }
107
+ return { schema: undefined, parentSchema, propertyKey };
108
+ }
109
+ return { schema: cursor, parentSchema, propertyKey };
110
+ }
111
+ function isRequired(parentSchema, propertyKey) {
112
+ return Boolean(propertyKey && parentSchema?.required?.includes(propertyKey));
113
+ }
114
+ function isScalarSchema(schema) {
115
+ return getSchemaTypes(schema).some((type) => ["string", "number", "integer", "boolean"].includes(type));
116
+ }
117
+ function isArraySchema(schema) {
118
+ return getSchemaTypes(schema).includes("array");
119
+ }
120
+ function isObjectSchema(schema) {
121
+ return getSchemaTypes(schema).includes("object");
122
+ }
123
+ function normalizeEnumValue(value) {
124
+ return value.trim().replace(/\s+/g, " ").toLowerCase();
125
+ }
126
+ function enumNormalizeHasMatch(schema, value) {
127
+ const normalized = normalizeEnumValue(value);
128
+ return getEnumValues(schema).filter((candidate) => normalizeEnumValue(candidate) === normalized).length === 1;
129
+ }
130
+ function isEmptyObject(value) {
131
+ return isRecord(value) && Object.keys(value).length === 0;
132
+ }
133
+ function isScalarValue(value) {
134
+ return ["string", "number", "boolean"].includes(typeof value);
135
+ }
136
+ function getParentPath(path) {
137
+ return path.slice(0, -1);
138
+ }
139
+ function isNumericArrayParentIssue(args, rootSchema, path) {
140
+ if (path.length === 0)
141
+ return undefined;
142
+ const parentPath = getParentPath(path);
143
+ const parentLookup = resolveSchemaAtPath(rootSchema, parentPath);
144
+ const parentSchema = parentLookup.schema;
145
+ if (!parentSchema || !isArraySchema(parentSchema) || Array.isArray(parentSchema.items))
146
+ return undefined;
147
+ if (!isJsonSchemaObject(parentSchema.items))
148
+ return undefined;
149
+ const itemTypes = getSchemaTypes(parentSchema.items);
150
+ if (!itemTypes.some((type) => type === "number" || type === "integer"))
151
+ return undefined;
152
+ const parentValue = getValueAtPath(args, parentPath);
153
+ if (!Array.isArray(parentValue) || !parentValue.every((item) => typeof item === "string"))
154
+ return undefined;
155
+ return {
156
+ path: parentPath,
157
+ pathText: formatRepairPath(parentPath),
158
+ value: parentValue,
159
+ schema: parentSchema,
160
+ parentSchema: parentLookup.parentSchema,
161
+ parentValue: getValueAtPath(args, getParentPath(parentPath)),
162
+ propertyKey: parentLookup.propertyKey,
163
+ required: isRequired(parentLookup.parentSchema, parentLookup.propertyKey),
164
+ modes: ["stringifiedNumberInArray"],
165
+ };
166
+ }
167
+ function classifyModes(toolName, issue) {
168
+ const modes = [];
169
+ const expectedTypes = getSchemaTypes(issue.schema);
170
+ if (toolName === "bash" && issue.pathText === "command") {
171
+ if (Array.isArray(issue.value) && issue.value.every((item) => typeof item === "string")) {
172
+ modes.push("bashCommandArgvJoin");
173
+ }
174
+ if (isRecord(issue.value)) {
175
+ modes.push("bashCommandUnwrap");
176
+ }
177
+ }
178
+ if (typeof issue.value === "string" && (isArraySchema(issue.schema) || isObjectSchema(issue.schema))) {
179
+ modes.push("jsonStringParse");
180
+ }
181
+ if (isArraySchema(issue.schema) && isRecord(issue.value)) {
182
+ modes.push("singleObjectWrap", "emptyObjectPlaceholder");
183
+ }
184
+ if (isArraySchema(issue.schema) && isScalarValue(issue.value)) {
185
+ modes.push("bareScalarWrap");
186
+ }
187
+ if (typeof issue.value === "string" && expectedTypes.some((type) => type === "number" || type === "integer")) {
188
+ modes.push("numberFromString");
189
+ }
190
+ if (typeof issue.value === "string" && expectedTypes.includes("boolean")) {
191
+ modes.push("boolFromString");
192
+ }
193
+ if (typeof issue.value === "string" && enumNormalizeHasMatch(issue.schema, issue.value)) {
194
+ modes.push("enumCaseNormalize");
195
+ }
196
+ if (Array.isArray(issue.value) && issue.value.length === 1 && isScalarSchema(issue.schema)) {
197
+ modes.push("singleElementUnwrap");
198
+ }
199
+ if (!issue.required && isEmptyObject(issue.value) && isScalarSchema(issue.schema)) {
200
+ modes.push("emptyObjectPlaceholder");
201
+ }
202
+ if (issue.value === null) {
203
+ modes.push(issue.required ? "nullRequiredBounce" : "nullOptionalDrop");
204
+ }
205
+ return modes;
206
+ }
207
+ function comparePaths(a, b) {
208
+ const length = Math.min(a.length, b.length);
209
+ for (let index = 0; index < length; index++) {
210
+ const left = a[index];
211
+ const right = b[index];
212
+ const leftNumber = Number(left);
213
+ const rightNumber = Number(right);
214
+ if (Number.isInteger(leftNumber) && Number.isInteger(rightNumber) && leftNumber !== rightNumber) {
215
+ return leftNumber - rightNumber;
216
+ }
217
+ if (left !== right)
218
+ return left < right ? -1 : 1;
219
+ }
220
+ return a.length - b.length;
221
+ }
222
+ export function analyzeToolArgumentErrors(toolName, schema, args, errors) {
223
+ const rootSchema = schema;
224
+ const issues = new Map();
225
+ for (const error of errors) {
226
+ if (error.keyword === "required")
227
+ continue;
228
+ const path = parseInstancePath(error.instancePath);
229
+ const numericArrayIssue = isNumericArrayParentIssue(args, rootSchema, path);
230
+ if (numericArrayIssue) {
231
+ issues.set(numericArrayIssue.pathText, numericArrayIssue);
232
+ continue;
233
+ }
234
+ const lookup = resolveSchemaAtPath(rootSchema, path);
235
+ if (!lookup.schema)
236
+ continue;
237
+ const value = getValueAtPath(args, path);
238
+ const issueBase = {
239
+ path,
240
+ pathText: formatRepairPath(path),
241
+ value,
242
+ schema: lookup.schema,
243
+ parentSchema: lookup.parentSchema,
244
+ parentValue: getValueAtPath(args, getParentPath(path)),
245
+ propertyKey: lookup.propertyKey,
246
+ required: isRequired(lookup.parentSchema, lookup.propertyKey),
247
+ };
248
+ const modes = classifyModes(toolName, issueBase);
249
+ if (modes.length > 0) {
250
+ issues.set(issueBase.pathText, { ...issueBase, modes });
251
+ }
252
+ }
253
+ return [...issues.values()].sort((left, right) => comparePaths(left.path, right.path));
254
+ }
255
+ //# sourceMappingURL=analyzer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"analyzer.js","sourceRoot":"","sources":["../../../src/utils/tool-repair/analyzer.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Tool } from \"../../types.ts\";\nimport type { ToolRepairModeName } from \"./registry.ts\";\n\nexport interface JsonSchemaObject {\n\ttype?: string | string[];\n\tproperties?: Record<string, JsonSchemaObject>;\n\titems?: JsonSchemaObject | JsonSchemaObject[];\n\trequired?: string[];\n\tadditionalProperties?: boolean | JsonSchemaObject;\n\tallOf?: JsonSchemaObject[];\n\tanyOf?: JsonSchemaObject[];\n\toneOf?: JsonSchemaObject[];\n\tenum?: unknown[];\n\tconst?: unknown;\n\tdefault?: unknown;\n}\n\nexport interface ValidationErrorLike {\n\tinstancePath: string;\n\tkeyword: string;\n\tmessage: string;\n}\n\nexport interface ToolRepairIssue {\n\tpath: string[];\n\tpathText: string;\n\tvalue: unknown;\n\tschema: JsonSchemaObject;\n\tparentSchema?: JsonSchemaObject;\n\tparentValue?: unknown;\n\tpropertyKey?: string;\n\trequired: boolean;\n\tmodes: ToolRepairModeName[];\n}\n\nexport function isRecord(value: unknown): value is Record<string, unknown> {\n\treturn typeof value === \"object\" && value !== null && !Array.isArray(value);\n}\n\nexport function isJsonSchemaObject(value: unknown): value is JsonSchemaObject {\n\treturn isRecord(value);\n}\n\nexport function parseInstancePath(instancePath: string): string[] {\n\tif (!instancePath) return [];\n\treturn instancePath\n\t\t.replace(/^\\//, \"\")\n\t\t.split(\"/\")\n\t\t.filter((segment) => segment.length > 0)\n\t\t.map((segment) => segment.replace(/~1/g, \"/\").replace(/~0/g, \"~\"));\n}\n\nexport function formatRepairPath(path: readonly string[]): string {\n\treturn path.length === 0 ? \"root\" : path.join(\".\");\n}\n\nexport function getValueAtPath(value: unknown, path: readonly string[]): unknown {\n\tlet cursor = value;\n\tfor (const segment of path) {\n\t\tif (Array.isArray(cursor)) {\n\t\t\tconst index = Number(segment);\n\t\t\tif (!Number.isInteger(index)) return undefined;\n\t\t\tcursor = cursor[index];\n\t\t} else if (isRecord(cursor)) {\n\t\t\tcursor = cursor[segment];\n\t\t} else {\n\t\t\treturn undefined;\n\t\t}\n\t}\n\treturn cursor;\n}\n\nexport function getSchemaTypes(schema: JsonSchemaObject): string[] {\n\tconst types = new Set<string>();\n\tconst addTypes = (candidate: JsonSchemaObject): void => {\n\t\tif (typeof candidate.type === \"string\") {\n\t\t\ttypes.add(candidate.type);\n\t\t} else if (Array.isArray(candidate.type)) {\n\t\t\tfor (const type of candidate.type) {\n\t\t\t\tif (typeof type === \"string\") types.add(type);\n\t\t\t}\n\t\t}\n\t\tif (candidate.enum?.every((value) => typeof value === \"string\")) {\n\t\t\ttypes.add(\"string\");\n\t\t}\n\t\tif (typeof candidate.const === \"string\") {\n\t\t\ttypes.add(\"string\");\n\t\t}\n\t};\n\n\taddTypes(schema);\n\tfor (const nested of [...(schema.anyOf ?? []), ...(schema.oneOf ?? []), ...(schema.allOf ?? [])]) {\n\t\taddTypes(nested);\n\t}\n\treturn [...types];\n}\n\nexport function getEnumValues(schema: JsonSchemaObject): string[] {\n\tconst values: string[] = [];\n\tconst addValues = (candidate: JsonSchemaObject): void => {\n\t\tif (Array.isArray(candidate.enum)) {\n\t\t\tfor (const value of candidate.enum) {\n\t\t\t\tif (typeof value === \"string\") values.push(value);\n\t\t\t}\n\t\t}\n\t\tif (typeof candidate.const === \"string\") {\n\t\t\tvalues.push(candidate.const);\n\t\t}\n\t};\n\n\taddValues(schema);\n\tfor (const nested of [...(schema.anyOf ?? []), ...(schema.oneOf ?? [])]) {\n\t\taddValues(nested);\n\t}\n\treturn values;\n}\n\nexport function resolveSchemaAtPath(\n\tschema: JsonSchemaObject,\n\tpath: readonly string[],\n): {\n\tschema?: JsonSchemaObject;\n\tparentSchema?: JsonSchemaObject;\n\tpropertyKey?: string;\n} {\n\tlet cursor: JsonSchemaObject | undefined = schema;\n\tlet parentSchema: JsonSchemaObject | undefined;\n\tlet propertyKey: string | undefined;\n\n\tfor (const segment of path) {\n\t\tif (!cursor) return { schema: undefined, parentSchema, propertyKey };\n\t\tparentSchema = cursor;\n\t\tpropertyKey = segment;\n\t\tif (cursor.properties?.[segment]) {\n\t\t\tcursor = cursor.properties[segment];\n\t\t\tcontinue;\n\t\t}\n\t\tif (Array.isArray(cursor.items)) {\n\t\t\tconst index = Number(segment);\n\t\t\tcursor = Number.isInteger(index) ? cursor.items[index] : undefined;\n\t\t\tcontinue;\n\t\t}\n\t\tif (isJsonSchemaObject(cursor.items)) {\n\t\t\tcursor = cursor.items;\n\t\t\tcontinue;\n\t\t}\n\t\tif (isJsonSchemaObject(cursor.additionalProperties)) {\n\t\t\tcursor = cursor.additionalProperties;\n\t\t\tcontinue;\n\t\t}\n\t\treturn { schema: undefined, parentSchema, propertyKey };\n\t}\n\n\treturn { schema: cursor, parentSchema, propertyKey };\n}\n\nfunction isRequired(parentSchema: JsonSchemaObject | undefined, propertyKey: string | undefined): boolean {\n\treturn Boolean(propertyKey && parentSchema?.required?.includes(propertyKey));\n}\n\nfunction isScalarSchema(schema: JsonSchemaObject): boolean {\n\treturn getSchemaTypes(schema).some((type) => [\"string\", \"number\", \"integer\", \"boolean\"].includes(type));\n}\n\nfunction isArraySchema(schema: JsonSchemaObject): boolean {\n\treturn getSchemaTypes(schema).includes(\"array\");\n}\n\nfunction isObjectSchema(schema: JsonSchemaObject): boolean {\n\treturn getSchemaTypes(schema).includes(\"object\");\n}\n\nfunction normalizeEnumValue(value: string): string {\n\treturn value.trim().replace(/\\s+/g, \" \").toLowerCase();\n}\n\nfunction enumNormalizeHasMatch(schema: JsonSchemaObject, value: string): boolean {\n\tconst normalized = normalizeEnumValue(value);\n\treturn getEnumValues(schema).filter((candidate) => normalizeEnumValue(candidate) === normalized).length === 1;\n}\n\nfunction isEmptyObject(value: unknown): boolean {\n\treturn isRecord(value) && Object.keys(value).length === 0;\n}\n\nfunction isScalarValue(value: unknown): boolean {\n\treturn [\"string\", \"number\", \"boolean\"].includes(typeof value);\n}\n\nfunction getParentPath(path: readonly string[]): string[] {\n\treturn path.slice(0, -1);\n}\n\nfunction isNumericArrayParentIssue(\n\targs: Record<string, unknown>,\n\trootSchema: JsonSchemaObject,\n\tpath: readonly string[],\n): ToolRepairIssue | undefined {\n\tif (path.length === 0) return undefined;\n\tconst parentPath = getParentPath(path);\n\tconst parentLookup = resolveSchemaAtPath(rootSchema, parentPath);\n\tconst parentSchema = parentLookup.schema;\n\tif (!parentSchema || !isArraySchema(parentSchema) || Array.isArray(parentSchema.items)) return undefined;\n\tif (!isJsonSchemaObject(parentSchema.items)) return undefined;\n\tconst itemTypes = getSchemaTypes(parentSchema.items);\n\tif (!itemTypes.some((type) => type === \"number\" || type === \"integer\")) return undefined;\n\tconst parentValue = getValueAtPath(args, parentPath);\n\tif (!Array.isArray(parentValue) || !parentValue.every((item) => typeof item === \"string\")) return undefined;\n\treturn {\n\t\tpath: parentPath,\n\t\tpathText: formatRepairPath(parentPath),\n\t\tvalue: parentValue,\n\t\tschema: parentSchema,\n\t\tparentSchema: parentLookup.parentSchema,\n\t\tparentValue: getValueAtPath(args, getParentPath(parentPath)),\n\t\tpropertyKey: parentLookup.propertyKey,\n\t\trequired: isRequired(parentLookup.parentSchema, parentLookup.propertyKey),\n\t\tmodes: [\"stringifiedNumberInArray\"],\n\t};\n}\n\nfunction classifyModes(toolName: string, issue: Omit<ToolRepairIssue, \"modes\">): ToolRepairModeName[] {\n\tconst modes: ToolRepairModeName[] = [];\n\tconst expectedTypes = getSchemaTypes(issue.schema);\n\n\tif (toolName === \"bash\" && issue.pathText === \"command\") {\n\t\tif (Array.isArray(issue.value) && issue.value.every((item) => typeof item === \"string\")) {\n\t\t\tmodes.push(\"bashCommandArgvJoin\");\n\t\t}\n\t\tif (isRecord(issue.value)) {\n\t\t\tmodes.push(\"bashCommandUnwrap\");\n\t\t}\n\t}\n\n\tif (typeof issue.value === \"string\" && (isArraySchema(issue.schema) || isObjectSchema(issue.schema))) {\n\t\tmodes.push(\"jsonStringParse\");\n\t}\n\tif (isArraySchema(issue.schema) && isRecord(issue.value)) {\n\t\tmodes.push(\"singleObjectWrap\", \"emptyObjectPlaceholder\");\n\t}\n\tif (isArraySchema(issue.schema) && isScalarValue(issue.value)) {\n\t\tmodes.push(\"bareScalarWrap\");\n\t}\n\tif (typeof issue.value === \"string\" && expectedTypes.some((type) => type === \"number\" || type === \"integer\")) {\n\t\tmodes.push(\"numberFromString\");\n\t}\n\tif (typeof issue.value === \"string\" && expectedTypes.includes(\"boolean\")) {\n\t\tmodes.push(\"boolFromString\");\n\t}\n\tif (typeof issue.value === \"string\" && enumNormalizeHasMatch(issue.schema, issue.value)) {\n\t\tmodes.push(\"enumCaseNormalize\");\n\t}\n\tif (Array.isArray(issue.value) && issue.value.length === 1 && isScalarSchema(issue.schema)) {\n\t\tmodes.push(\"singleElementUnwrap\");\n\t}\n\tif (!issue.required && isEmptyObject(issue.value) && isScalarSchema(issue.schema)) {\n\t\tmodes.push(\"emptyObjectPlaceholder\");\n\t}\n\tif (issue.value === null) {\n\t\tmodes.push(issue.required ? \"nullRequiredBounce\" : \"nullOptionalDrop\");\n\t}\n\n\treturn modes;\n}\n\nfunction comparePaths(a: readonly string[], b: readonly string[]): number {\n\tconst length = Math.min(a.length, b.length);\n\tfor (let index = 0; index < length; index++) {\n\t\tconst left = a[index];\n\t\tconst right = b[index];\n\t\tconst leftNumber = Number(left);\n\t\tconst rightNumber = Number(right);\n\t\tif (Number.isInteger(leftNumber) && Number.isInteger(rightNumber) && leftNumber !== rightNumber) {\n\t\t\treturn leftNumber - rightNumber;\n\t\t}\n\t\tif (left !== right) return left < right ? -1 : 1;\n\t}\n\treturn a.length - b.length;\n}\n\nexport function analyzeToolArgumentErrors(\n\ttoolName: string,\n\tschema: Tool[\"parameters\"],\n\targs: Record<string, unknown>,\n\terrors: readonly ValidationErrorLike[],\n): ToolRepairIssue[] {\n\tconst rootSchema = schema as JsonSchemaObject;\n\tconst issues = new Map<string, ToolRepairIssue>();\n\n\tfor (const error of errors) {\n\t\tif (error.keyword === \"required\") continue;\n\t\tconst path = parseInstancePath(error.instancePath);\n\t\tconst numericArrayIssue = isNumericArrayParentIssue(args, rootSchema, path);\n\t\tif (numericArrayIssue) {\n\t\t\tissues.set(numericArrayIssue.pathText, numericArrayIssue);\n\t\t\tcontinue;\n\t\t}\n\n\t\tconst lookup = resolveSchemaAtPath(rootSchema, path);\n\t\tif (!lookup.schema) continue;\n\t\tconst value = getValueAtPath(args, path);\n\t\tconst issueBase = {\n\t\t\tpath,\n\t\t\tpathText: formatRepairPath(path),\n\t\t\tvalue,\n\t\t\tschema: lookup.schema,\n\t\t\tparentSchema: lookup.parentSchema,\n\t\t\tparentValue: getValueAtPath(args, getParentPath(path)),\n\t\t\tpropertyKey: lookup.propertyKey,\n\t\t\trequired: isRequired(lookup.parentSchema, lookup.propertyKey),\n\t\t};\n\t\tconst modes = classifyModes(toolName, issueBase);\n\t\tif (modes.length > 0) {\n\t\t\tissues.set(issueBase.pathText, { ...issueBase, modes });\n\t\t}\n\t}\n\n\treturn [...issues.values()].sort((left, right) => comparePaths(left.path, right.path));\n}\n"]}
@@ -0,0 +1,32 @@
1
+ export declare const TOOL_REPAIR_MODE_NAMES: readonly ["nullOptionalDrop", "nullRequiredBounce", "jsonStringParse", "singleObjectWrap", "bareScalarWrap", "emptyObjectPlaceholder", "numberFromString", "boolFromString", "enumCaseNormalize", "singleElementUnwrap", "stringifiedNumberInArray", "bashCommandArgvJoin", "bashCommandUnwrap"];
2
+ export type ToolRepairModeName = (typeof TOOL_REPAIR_MODE_NAMES)[number];
3
+ export type ToolRepairFailureModeName = ToolRepairModeName | "other";
4
+ export interface ToolRepairRegistryEntry {
5
+ name: ToolRepairModeName;
6
+ noteTemplate: string;
7
+ standingRule: string;
8
+ }
9
+ export declare const TOOL_REPAIR_REGISTRY: readonly ToolRepairRegistryEntry[];
10
+ export declare function getToolRepairRegistryEntry(name: ToolRepairModeName): ToolRepairRegistryEntry;
11
+ export declare function formatToolRepairNote(name: ToolRepairModeName, path: string): string;
12
+ export declare function formatToolRepairStandingRule(name: ToolRepairModeName): string;
13
+ export declare const TOOL_EXECUTION_ERROR_CATALOGUE: readonly [{
14
+ readonly name: "commandNotFound";
15
+ readonly guidance: "Command was not found; check the command name or available tools before retrying.";
16
+ readonly matches: (message: string) => boolean;
17
+ }, {
18
+ readonly name: "fileNotFound";
19
+ readonly guidance: "Path was not found; list the parent directory or re-read the path before retrying.";
20
+ readonly matches: (message: string) => boolean;
21
+ }, {
22
+ readonly name: "editOldTextNotFound";
23
+ readonly guidance: "Re-read the target file and use the exact current text before retrying.";
24
+ readonly matches: (message: string) => boolean;
25
+ }, {
26
+ readonly name: "pathOutsideCwd";
27
+ readonly guidance: "Choose a path inside the current working directory, or ask before changing scope.";
28
+ readonly matches: (message: string) => boolean;
29
+ }];
30
+ export type ToolExecutionErrorClass = (typeof TOOL_EXECUTION_ERROR_CATALOGUE)[number]["name"];
31
+ export declare function getToolExecutionErrorGuidance(errorMessage: string): string | undefined;
32
+ //# sourceMappingURL=registry.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"registry.d.ts","sourceRoot":"","sources":["../../../src/utils/tool-repair/registry.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,sBAAsB,kSAczB,CAAC;AAEX,MAAM,MAAM,kBAAkB,GAAG,CAAC,OAAO,sBAAsB,CAAC,CAAC,MAAM,CAAC,CAAC;AACzE,MAAM,MAAM,yBAAyB,GAAG,kBAAkB,GAAG,OAAO,CAAC;AAErE,MAAM,WAAW,uBAAuB;IACvC,IAAI,EAAE,kBAAkB,CAAC;IACzB,YAAY,EAAE,MAAM,CAAC;IACrB,YAAY,EAAE,MAAM,CAAC;CACrB;AAED,eAAO,MAAM,oBAAoB,EAAE,SAAS,uBAAuB,EAoEzD,CAAC;AAIX,wBAAgB,0BAA0B,CAAC,IAAI,EAAE,kBAAkB,GAAG,uBAAuB,CAI5F;AAED,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,kBAAkB,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,CAEnF;AAED,wBAAgB,4BAA4B,CAAC,IAAI,EAAE,kBAAkB,GAAG,MAAM,CAE7E;AAED,eAAO,MAAM,8BAA8B;;;;;;;;;;;;;;;;EA6BjC,CAAC;AAEX,MAAM,MAAM,uBAAuB,GAAG,CAAC,OAAO,8BAA8B,CAAC,CAAC,MAAM,CAAC,CAAC,MAAM,CAAC,CAAC;AAE9F,wBAAgB,6BAA6B,CAAC,YAAY,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAEtF","sourcesContent":["export const TOOL_REPAIR_MODE_NAMES = [\n\t\"nullOptionalDrop\",\n\t\"nullRequiredBounce\",\n\t\"jsonStringParse\",\n\t\"singleObjectWrap\",\n\t\"bareScalarWrap\",\n\t\"emptyObjectPlaceholder\",\n\t\"numberFromString\",\n\t\"boolFromString\",\n\t\"enumCaseNormalize\",\n\t\"singleElementUnwrap\",\n\t\"stringifiedNumberInArray\",\n\t\"bashCommandArgvJoin\",\n\t\"bashCommandUnwrap\",\n] as const;\n\nexport type ToolRepairModeName = (typeof TOOL_REPAIR_MODE_NAMES)[number];\nexport type ToolRepairFailureModeName = ToolRepairModeName | \"other\";\n\nexport interface ToolRepairRegistryEntry {\n\tname: ToolRepairModeName;\n\tnoteTemplate: string;\n\tstandingRule: string;\n}\n\nexport const TOOL_REPAIR_REGISTRY: readonly ToolRepairRegistryEntry[] = [\n\t{\n\t\tname: \"nullOptionalDrop\",\n\t\tnoteTemplate: \"sent null for optional `{path}` -> omit the field instead\",\n\t\tstandingRule: \"Omit optional fields instead of sending null.\",\n\t},\n\t{\n\t\tname: \"nullRequiredBounce\",\n\t\tnoteTemplate: \"`{path}` is required and cannot be null -> send a real value\",\n\t\tstandingRule: \"Send real values for required fields; never send null for a required field.\",\n\t},\n\t{\n\t\tname: \"jsonStringParse\",\n\t\tnoteTemplate: \"sent `{path}` as a quoted JSON string -> send a raw JSON array/object\",\n\t\tstandingRule:\n\t\t\t\"Send raw JSON arrays/objects where the tool schema expects arrays/objects; do not quote them as JSON strings.\",\n\t},\n\t{\n\t\tname: \"singleObjectWrap\",\n\t\tnoteTemplate: \"sent one object where `{path}` takes a list -> wrap it in [ ]\",\n\t\tstandingRule: \"Wrap a single object in [ ] when the tool schema expects a list.\",\n\t},\n\t{\n\t\tname: \"bareScalarWrap\",\n\t\tnoteTemplate: \"sent a single value where `{path}` takes a list -> wrap it in [ ]\",\n\t\tstandingRule: \"Wrap a single scalar in [ ] when the tool schema expects a list.\",\n\t},\n\t{\n\t\tname: \"emptyObjectPlaceholder\",\n\t\tnoteTemplate: \"sent `{}` as a placeholder -> omit `{path}`; its default applies\",\n\t\tstandingRule: \"Omit defaulted object fields instead of sending `{}` placeholders.\",\n\t},\n\t{\n\t\tname: \"numberFromString\",\n\t\tnoteTemplate: \"sent `{path}` as a quoted number -> send a bare number\",\n\t\tstandingRule: \"Send bare numbers where the tool schema expects numbers; do not quote them.\",\n\t},\n\t{\n\t\tname: \"boolFromString\",\n\t\tnoteTemplate: \"sent `{path}` as a quoted boolean -> send bare true/false\",\n\t\tstandingRule: \"Send bare true/false where the tool schema expects booleans; do not quote them.\",\n\t},\n\t{\n\t\tname: \"enumCaseNormalize\",\n\t\tnoteTemplate: \"`{path}` matched a declared enum value after case/space normalization\",\n\t\tstandingRule: \"Use enum values exactly as declared, preserving case and spacing.\",\n\t},\n\t{\n\t\tname: \"singleElementUnwrap\",\n\t\tnoteTemplate: \"sent `{path}` as a 1-item list where a single value was expected -> send the value\",\n\t\tstandingRule:\n\t\t\t\"Send a single value directly when the tool schema expects a single value; do not wrap it in a one-item list.\",\n\t},\n\t{\n\t\tname: \"stringifiedNumberInArray\",\n\t\tnoteTemplate: \"list `{path}` holds quoted numbers -> send bare numbers\",\n\t\tstandingRule: \"Use bare numbers inside number arrays; do not quote them.\",\n\t},\n\t{\n\t\tname: \"bashCommandArgvJoin\",\n\t\tnoteTemplate: \"bash takes one command string, not an argv list -> joined the argv values\",\n\t\tstandingRule: \"For bash, send one command string rather than an argv array.\",\n\t},\n\t{\n\t\tname: \"bashCommandUnwrap\",\n\t\tnoteTemplate: \"bash `command` is a string -> unwrapped the command object\",\n\t\tstandingRule: \"For bash, send `command` as a string rather than an object wrapper.\",\n\t},\n] as const;\n\nconst registryByName = new Map(TOOL_REPAIR_REGISTRY.map((entry) => [entry.name, entry]));\n\nexport function getToolRepairRegistryEntry(name: ToolRepairModeName): ToolRepairRegistryEntry {\n\tconst entry = registryByName.get(name);\n\tif (!entry) throw new Error(`Unknown tool repair mode: ${name}`);\n\treturn entry;\n}\n\nexport function formatToolRepairNote(name: ToolRepairModeName, path: string): string {\n\treturn getToolRepairRegistryEntry(name).noteTemplate.replaceAll(\"{path}\", path);\n}\n\nexport function formatToolRepairStandingRule(name: ToolRepairModeName): string {\n\treturn getToolRepairRegistryEntry(name).standingRule;\n}\n\nexport const TOOL_EXECUTION_ERROR_CATALOGUE = [\n\t{\n\t\tname: \"commandNotFound\",\n\t\tguidance: \"Command was not found; check the command name or available tools before retrying.\",\n\t\tmatches(message: string): boolean {\n\t\t\treturn /^spawn \\S+ ENOENT\\b/i.test(message) || /(?:^|\\n|:)\\s*command not found\\b/i.test(message);\n\t\t},\n\t},\n\t{\n\t\tname: \"fileNotFound\",\n\t\tguidance: \"Path was not found; list the parent directory or re-read the path before retrying.\",\n\t\tmatches(message: string): boolean {\n\t\t\treturn /\\bENOENT\\b/i.test(message) || /no such file or directory/i.test(message);\n\t\t},\n\t},\n\t{\n\t\tname: \"editOldTextNotFound\",\n\t\tguidance: \"Re-read the target file and use the exact current text before retrying.\",\n\t\tmatches(message: string): boolean {\n\t\t\treturn /(?:oldText|old text|exact text).*(?:not found|no match|failed to match|must match)/is.test(message);\n\t\t},\n\t},\n\t{\n\t\tname: \"pathOutsideCwd\",\n\t\tguidance: \"Choose a path inside the current working directory, or ask before changing scope.\",\n\t\tmatches(message: string): boolean {\n\t\t\treturn /outside (?:the )?(?:current working directory|cwd|workspace|root)/i.test(message);\n\t\t},\n\t},\n] as const;\n\nexport type ToolExecutionErrorClass = (typeof TOOL_EXECUTION_ERROR_CATALOGUE)[number][\"name\"];\n\nexport function getToolExecutionErrorGuidance(errorMessage: string): string | undefined {\n\treturn TOOL_EXECUTION_ERROR_CATALOGUE.find((entry) => entry.matches(errorMessage))?.guidance;\n}\n"]}