@theokit/sdk 2.15.0 → 2.15.1
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/CHANGELOG.md +6 -0
- package/dist/a2a/index.cjs +30 -7
- package/dist/a2a/index.cjs.map +1 -1
- package/dist/a2a/index.js +30 -7
- package/dist/a2a/index.js.map +1 -1
- package/dist/cron.cjs +30 -7
- package/dist/cron.cjs.map +1 -1
- package/dist/cron.js +30 -7
- package/dist/cron.js.map +1 -1
- package/dist/eval.cjs +30 -7
- package/dist/eval.cjs.map +1 -1
- package/dist/eval.js +30 -7
- package/dist/eval.js.map +1 -1
- package/dist/index.cjs +30 -7
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +30 -7
- package/dist/index.js.map +1 -1
- package/dist/internal/llm/hermes-tool-extract.d.ts +5 -1
- package/dist/internal/llm/openai.d.ts +5 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -13647,11 +13647,16 @@ function sanitizeToolInput(input, options) {
|
|
|
13647
13647
|
// src/internal/llm/hermes-tool-extract.ts
|
|
13648
13648
|
var HERMES_BLOCK = /<function=\s*([^>\s]+)\s*>([\s\S]*?)<\/tool_call>/g;
|
|
13649
13649
|
var HERMES_PARAM = /<parameter=\s*([^>\s]+)\s*>([\s\S]*?)<\/parameter>/g;
|
|
13650
|
-
function extractHermesToolCalls(content, makeId) {
|
|
13650
|
+
function extractHermesToolCalls(content, makeId, allowedToolNames) {
|
|
13651
|
+
const isPromoted = (name) => name.length > 0 && (allowedToolNames === void 0 || allowedToolNames.has(name));
|
|
13651
13652
|
const toolCalls = [];
|
|
13653
|
+
const droppedNames = [];
|
|
13652
13654
|
for (const block of content.matchAll(HERMES_BLOCK)) {
|
|
13653
13655
|
const name = (block[1] ?? "").trim();
|
|
13654
|
-
if (name
|
|
13656
|
+
if (!isPromoted(name)) {
|
|
13657
|
+
if (name.length > 0 && allowedToolNames !== void 0) droppedNames.push(name);
|
|
13658
|
+
continue;
|
|
13659
|
+
}
|
|
13655
13660
|
toolCalls.push({
|
|
13656
13661
|
type: "tool_use",
|
|
13657
13662
|
id: makeId(),
|
|
@@ -13659,8 +13664,11 @@ function extractHermesToolCalls(content, makeId) {
|
|
|
13659
13664
|
input: parseHermesParams(block[2] ?? "")
|
|
13660
13665
|
});
|
|
13661
13666
|
}
|
|
13662
|
-
const residualText = toolCalls.length === 0 ? content : content.replace(
|
|
13663
|
-
|
|
13667
|
+
const residualText = toolCalls.length === 0 ? content : content.replace(
|
|
13668
|
+
HERMES_BLOCK,
|
|
13669
|
+
(full, rawName) => isPromoted((rawName ?? "").trim()) ? "" : full
|
|
13670
|
+
).trim();
|
|
13671
|
+
return { toolCalls, residualText, droppedNames };
|
|
13664
13672
|
}
|
|
13665
13673
|
function parseHermesParams(inner) {
|
|
13666
13674
|
const input = {};
|
|
@@ -13744,7 +13752,10 @@ var OpenAIClient = class {
|
|
|
13744
13752
|
}
|
|
13745
13753
|
const accumulator = new OpenAIStreamAccumulator(
|
|
13746
13754
|
this.options.extractToolCallsFromContent ?? false,
|
|
13747
|
-
providerId
|
|
13755
|
+
providerId,
|
|
13756
|
+
// R5: request-scoped allowlist — leaked recovery only promotes a block whose name is a tool the
|
|
13757
|
+
// model was actually given. Empty set (no tools) recovers nothing.
|
|
13758
|
+
new Set(request.tools?.map((tool) => tool.name) ?? [])
|
|
13748
13759
|
);
|
|
13749
13760
|
for await (const record of parseSseStream(response.body, signal)) {
|
|
13750
13761
|
if (record.data === "[DONE]") break;
|
|
@@ -13774,13 +13785,18 @@ var OpenAIStreamAccumulator = class {
|
|
|
13774
13785
|
/**
|
|
13775
13786
|
* @param extractFromContent opt-in leaked-dialect safe-parse (theokit#58). Default false.
|
|
13776
13787
|
* @param providerName provider id, used only to label the recovery log line.
|
|
13788
|
+
* @param allowedToolNames R5 request-scoped allowlist — built from `request.tools` at `stream()`;
|
|
13789
|
+
* leaked recovery in `finish()` only promotes a block whose name is in this set. `undefined`
|
|
13790
|
+
* (direct construction) recovers all (back-compat); an empty set recovers nothing.
|
|
13777
13791
|
*/
|
|
13778
|
-
constructor(extractFromContent = false, providerName = "openai") {
|
|
13792
|
+
constructor(extractFromContent = false, providerName = "openai", allowedToolNames) {
|
|
13779
13793
|
this.extractFromContent = extractFromContent;
|
|
13780
13794
|
this.providerName = providerName;
|
|
13795
|
+
this.allowedToolNames = allowedToolNames;
|
|
13781
13796
|
}
|
|
13782
13797
|
extractFromContent;
|
|
13783
13798
|
providerName;
|
|
13799
|
+
allowedToolNames;
|
|
13784
13800
|
text = "";
|
|
13785
13801
|
stopReason = "end_turn";
|
|
13786
13802
|
inputTokens;
|
|
@@ -13851,7 +13867,8 @@ var OpenAIStreamAccumulator = class {
|
|
|
13851
13867
|
if (this.extractFromContent && toolCalls.length === 0) {
|
|
13852
13868
|
const recovered = extractHermesToolCalls(
|
|
13853
13869
|
this.text,
|
|
13854
|
-
() => `hermes-${globalThis.crypto.randomUUID()}
|
|
13870
|
+
() => `hermes-${globalThis.crypto.randomUUID()}`,
|
|
13871
|
+
this.allowedToolNames
|
|
13855
13872
|
);
|
|
13856
13873
|
if (recovered.toolCalls.length > 0) {
|
|
13857
13874
|
toolCalls.push(...recovered.toolCalls);
|
|
@@ -13859,6 +13876,12 @@ var OpenAIStreamAccumulator = class {
|
|
|
13859
13876
|
stopReason = "tool_use";
|
|
13860
13877
|
process.stderr.write(
|
|
13861
13878
|
`[theokit-sdk] recovered ${recovered.toolCalls.length} leaked tool call(s) from assistant content (provider="${this.providerName}", names=${recovered.toolCalls.map((c) => c.name).join(",")})
|
|
13879
|
+
`
|
|
13880
|
+
);
|
|
13881
|
+
}
|
|
13882
|
+
if (recovered.droppedNames.length > 0) {
|
|
13883
|
+
process.stderr.write(
|
|
13884
|
+
`[theokit-sdk] dropped ${recovered.droppedNames.length} leaked block(s) whose name is not a tool in the request (provider="${this.providerName}", names=${recovered.droppedNames.join(",")})
|
|
13862
13885
|
`
|
|
13863
13886
|
);
|
|
13864
13887
|
}
|