@openclaw/ai 2026.7.2-beta.7 → 2026.8.1-beta.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{anthropic-CH4UUnZr.mjs → anthropic-B6dLpq5L.mjs} +55 -203
- package/dist/{src-QkygScBs.mjs → anthropic-JsNA5KCu.mjs} +0 -1
- package/dist/anthropic-compaction-replay-8lJNKXOE.mjs +840 -0
- package/dist/anthropic-payload-policy-CiEuQS72.d.mts +49 -0
- package/dist/{api-registry-DlMgPR39.d.mts → api-registry-k3zTz0cV.d.mts} +1 -1
- package/dist/{azure-openai-responses-CImcwB83.mjs → azure-openai-responses-mxIOtUnn.mjs} +23 -29
- package/dist/diagnostics.d.mts +24 -1
- package/dist/diagnostics.mjs +2 -1
- package/dist/{event-stream-YjaPW20U.d.mts → event-stream-BP6AWT8j.d.mts} +4 -1
- package/dist/{event-stream-D8n2uFee.mjs → event-stream-uSMZJ3FA.mjs} +26 -5
- package/dist/event-stream.d.mts +1 -1
- package/dist/event-stream.mjs +1 -1
- package/dist/{google-CtSg0iTS.mjs → google-C7h2QzDX.mjs} +5 -5
- package/dist/{google-shared-DNBz5rcD.mjs → google-shared-B0Qr9OR7.mjs} +146 -89
- package/dist/google-thinking-level-C-V3tecN.mjs +9 -0
- package/dist/{google-vertex-31f1uS9L.mjs → google-vertex-Bhc3TjDl.mjs} +11 -7
- package/dist/{llm-request-activity-BjtkplhG.mjs → headers-DdOQtGuU.mjs} +9 -1
- package/dist/host-DTqNc7ad.mjs +466 -0
- package/dist/{host-B9GUmcra.d.mts → host-vWgMMhiJ.d.mts} +9 -4
- package/dist/index.d.mts +6 -6
- package/dist/index.mjs +7 -5
- package/dist/internal/anthropic.d.mts +29 -5
- package/dist/internal/anthropic.mjs +5 -5
- package/dist/internal/openai-responses-payload-policy.d.mts +3 -0
- package/dist/internal/openai-responses-payload-policy.mjs +3 -0
- package/dist/internal/openai.d.mts +6 -6
- package/dist/internal/openai.mjs +8 -7
- package/dist/internal/runtime.d.mts +17 -5
- package/dist/internal/runtime.mjs +85 -73
- package/dist/internal/shared.d.mts +1 -6
- package/dist/internal/shared.mjs +3 -5
- package/dist/{json-parse-BvXNt1-7.mjs → json-parse-CDnesDM_.mjs} +4 -6
- package/dist/{mistral-CWmpvWYh.mjs → mistral-CEWoQI_g.mjs} +45 -48
- package/dist/number-coercion-H9qHik3g.mjs +71 -0
- package/dist/openai-chatgpt-jwt-KWcgd0d_.mjs +19 -0
- package/dist/{openai-chatgpt-responses-B84Ibtrd.mjs → openai-chatgpt-responses-CrPmqERt.mjs} +284 -240
- package/dist/{openai-completions-DsOxhOD1.mjs → openai-completions-BPnt4Sml.mjs} +65 -99
- package/dist/{openai-completions-compat-DBWjXoMZ.d.mts → openai-completions-compat-Dt3dcawL.d.mts} +2 -2
- package/dist/{openai-responses-BT7A3sLu.mjs → openai-responses-DhIKtOup.mjs} +18 -41
- package/dist/openai-responses-contracts-CyfIkQi5.mjs +253 -0
- package/dist/openai-responses-contracts-XpZJxrRG.d.mts +68 -0
- package/dist/openai-responses-payload-policy-BDxV-W0c.mjs +206 -0
- package/dist/openai-responses-payload-policy-BSs371VM.d.mts +40 -0
- package/dist/openai-responses-prompt-observer-internal-DgNTYnRY.mjs +46 -0
- package/dist/{openai-responses-stream-internal-Cw5txaGW.mjs → openai-responses-shared-DXIt3iY5.mjs} +1406 -940
- package/dist/{openai-reasoning-compat-YgeLncHw.mjs → openai-stop-reason-BkFkqqK0.mjs} +204 -37
- package/dist/openai-tool-projection-CY04OcvQ.mjs +338 -0
- package/dist/provider-error-BUwEnjXq.mjs +429 -0
- package/dist/provider-error-CzNw4BWX.d.mts +12 -0
- package/dist/{provider-options-D8bB3z9b.d.mts → provider-options-B96RdNpH.d.mts} +9 -3
- package/dist/provider-transcript-transform-ePx-Bbfr.mjs +155 -0
- package/dist/provider-types.d.mts +31 -0
- package/dist/provider-types.mjs +8 -0
- package/dist/providers.d.mts +1 -1
- package/dist/providers.mjs +17 -19
- package/dist/{reasoning-tag-text-partitioner-CGDyLWUR.mjs → reasoning-tag-text-partitioner-rnPwX2pg.mjs} +14 -8
- package/dist/record-coerce-DdXsgUd_.mjs +23 -0
- package/dist/sanitize-unicode-BYqrYtC_.mjs +90 -0
- package/dist/session-resources-CkR4WWy1.mjs +21 -0
- package/dist/simple-options-D58D5Kvw.mjs +117 -0
- package/dist/src-D2H6yKkH.mjs +2 -0
- package/dist/{stream-first-event-timeout-BBys9hSb.mjs → stream-first-event-timeout-MK28puvq.mjs} +2 -2
- package/dist/string-coerce-fsri9iCu.mjs +34 -0
- package/dist/{tool-schema-json-projection-BwNu3nDi.mjs → tool-schema-json-projection-q5d7QX5c.mjs} +32 -7
- package/dist/transport-utils-DJqkxbhC.mjs +138 -0
- package/dist/transports.d.mts +166 -241
- package/dist/transports.mjs +1979 -1825
- package/dist/types-BDdaOVi2.mjs +6 -0
- package/dist/{types-bzp5k29J.d.mts → types-BHNrPS1l.d.mts} +23 -1
- package/dist/types.d.mts +4 -4
- package/dist/types.mjs +6 -4
- package/dist/utf16-slice-CvGodqok.mjs +29 -0
- package/dist/{validation-DAa_yFOM.mjs → validation-B61OhAio.mjs} +6 -6
- package/dist/{validation-B-j7cOYp.d.mts → validation-DT9SrFn3.d.mts} +1 -1
- package/dist/validation.d.mts +1 -1
- package/dist/validation.mjs +1 -1
- package/package.json +15 -1
- package/dist/anthropic-usage-DWU-x8MI.mjs +0 -459
- package/dist/error-coercion-DgxlWC0n.mjs +0 -15
- package/dist/headers-B_e4-1J0.mjs +0 -9
- package/dist/host-Dog2WQiR.mjs +0 -369
- package/dist/number-coercion-DvG7SNMg.mjs +0 -129
- package/dist/openai-chatgpt-jwt-DhAAzLkj.mjs +0 -39
- package/dist/openai-responses-shared-pXl6Wd8S.mjs +0 -392
- package/dist/openai-tool-projection-OhX64DoP.mjs +0 -215
- package/dist/provider-error-CAEvRjry.mjs +0 -47
- package/dist/sanitize-unicode-DT5o51ur.mjs +0 -26
- package/dist/simple-options-9lhRrN73.mjs +0 -50
- package/dist/tool-result-text-CTpIRbYd.mjs +0 -225
- package/dist/transform-messages-C8mBqZxF.mjs +0 -2
- package/dist/transport-stream-shared-D81p90xq.mjs +0 -297
|
@@ -0,0 +1,429 @@
|
|
|
1
|
+
import { o as normalizeStringifiedOptionalString } from "./string-coerce-fsri9iCu.mjs";
|
|
2
|
+
import { i as asOptionalRecord } from "./record-coerce-DdXsgUd_.mjs";
|
|
3
|
+
import { t as truncateUtf16Safe } from "./utf16-slice-CvGodqok.mjs";
|
|
4
|
+
import "./number-coercion-H9qHik3g.mjs";
|
|
5
|
+
//#region packages/normalization-core/src/balanced-json.ts
|
|
6
|
+
function isJsonOpeningDelimiter(char, openers) {
|
|
7
|
+
return (char === "{" || char === "[") && openers.includes(char);
|
|
8
|
+
}
|
|
9
|
+
/** Extracts the first balanced JSON object/array from text. */
|
|
10
|
+
function extractBalancedJsonPrefix(raw, opts = {}) {
|
|
11
|
+
const openers = opts.openers ?? ["{", "["];
|
|
12
|
+
let start = 0;
|
|
13
|
+
while (start < raw.length && !isJsonOpeningDelimiter(raw[start], openers)) start += 1;
|
|
14
|
+
const stack = [];
|
|
15
|
+
let inString = false;
|
|
16
|
+
let escaped = false;
|
|
17
|
+
for (let index = start; index < raw.length; index += 1) {
|
|
18
|
+
const char = raw[index];
|
|
19
|
+
if (inString) {
|
|
20
|
+
if (escaped) escaped = false;
|
|
21
|
+
else if (char === "\\") escaped = true;
|
|
22
|
+
else if (char === "\"") inString = false;
|
|
23
|
+
} else if (char === "\"") inString = true;
|
|
24
|
+
else if (isJsonOpeningDelimiter(char, openers)) stack.push(char);
|
|
25
|
+
else if (stack.length > 0 && char === (stack.at(-1) === "{" ? "}" : "]")) {
|
|
26
|
+
stack.pop();
|
|
27
|
+
if (stack.length === 0) return {
|
|
28
|
+
json: raw.slice(start, index + 1),
|
|
29
|
+
startIndex: start,
|
|
30
|
+
endIndex: index
|
|
31
|
+
};
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
return null;
|
|
35
|
+
}
|
|
36
|
+
/** Extracts every balanced JSON object/array fragment from arbitrary text. */
|
|
37
|
+
function extractBalancedJsonFragments(raw, opts = {}) {
|
|
38
|
+
const fragments = [];
|
|
39
|
+
for (let offset = 0; offset < raw.length;) {
|
|
40
|
+
const fragment = extractBalancedJsonPrefix(raw.slice(offset), opts);
|
|
41
|
+
if (!fragment) break;
|
|
42
|
+
fragments.push({
|
|
43
|
+
json: fragment.json,
|
|
44
|
+
startIndex: offset + fragment.startIndex,
|
|
45
|
+
endIndex: offset + fragment.endIndex
|
|
46
|
+
});
|
|
47
|
+
offset += fragment.endIndex + 1;
|
|
48
|
+
}
|
|
49
|
+
return fragments;
|
|
50
|
+
}
|
|
51
|
+
//#endregion
|
|
52
|
+
//#region packages/normalization-core/src/stable-stringify.ts
|
|
53
|
+
const preserveString = (value) => value;
|
|
54
|
+
/** Deterministically stringifies values, optionally normalizing strings before key ordering. */
|
|
55
|
+
function stableStringify(value, normalizeString = preserveString) {
|
|
56
|
+
return stringifyStableValue(value, /* @__PURE__ */ new WeakSet(), normalizeString);
|
|
57
|
+
}
|
|
58
|
+
function stringifyStableValue(value, stack, normalizeString) {
|
|
59
|
+
if (value === null || value === void 0) return String(value);
|
|
60
|
+
if (typeof value === "number" && !Number.isFinite(value)) return JSON.stringify(String(value));
|
|
61
|
+
if (typeof value === "bigint") return JSON.stringify(value.toString());
|
|
62
|
+
if (typeof value === "string") return JSON.stringify(normalizeString(value));
|
|
63
|
+
if (typeof value !== "object") return JSON.stringify(value) ?? "null";
|
|
64
|
+
if (stack.has(value)) return JSON.stringify("[Circular]");
|
|
65
|
+
stack.add(value);
|
|
66
|
+
try {
|
|
67
|
+
return stringifyObjectValue(value, stack, normalizeString);
|
|
68
|
+
} finally {
|
|
69
|
+
stack.delete(value);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
function stringifyObjectValue(value, stack, normalizeString) {
|
|
73
|
+
if (value instanceof Error) return stringifyStableValue({
|
|
74
|
+
name: value.name,
|
|
75
|
+
message: value.message,
|
|
76
|
+
stack: value.stack
|
|
77
|
+
}, stack, normalizeString);
|
|
78
|
+
if (value instanceof Uint8Array) return stringifyStableValue({
|
|
79
|
+
type: "Uint8Array",
|
|
80
|
+
data: encodeBase64(value)
|
|
81
|
+
}, stack, normalizeString);
|
|
82
|
+
if (Array.isArray(value)) {
|
|
83
|
+
const serializedEntries = [];
|
|
84
|
+
for (const entry of value) serializedEntries.push(stringifyStableValue(entry, stack, normalizeString));
|
|
85
|
+
return `[${serializedEntries.join(",")}]`;
|
|
86
|
+
}
|
|
87
|
+
const record = value;
|
|
88
|
+
const entries = Object.keys(record).map((key) => ({
|
|
89
|
+
key,
|
|
90
|
+
normalizedKey: normalizeString(key)
|
|
91
|
+
})).toSorted((left, right) => {
|
|
92
|
+
return compareStableStrings(left.normalizedKey, right.normalizedKey) || compareStableStrings(left.key, right.key);
|
|
93
|
+
});
|
|
94
|
+
const serializedFields = [];
|
|
95
|
+
for (const { key, normalizedKey } of entries) serializedFields.push(`${JSON.stringify(normalizedKey)}:${stringifyStableValue(record[key], stack, normalizeString)}`);
|
|
96
|
+
return `{${serializedFields.join(",")}}`;
|
|
97
|
+
}
|
|
98
|
+
function encodeBase64(value) {
|
|
99
|
+
let binary = "";
|
|
100
|
+
for (const byte of value) binary += String.fromCharCode(byte);
|
|
101
|
+
return btoa(binary);
|
|
102
|
+
}
|
|
103
|
+
function compareStableStrings(left, right) {
|
|
104
|
+
return left < right ? -1 : left > right ? 1 : 0;
|
|
105
|
+
}
|
|
106
|
+
//#endregion
|
|
107
|
+
//#region packages/media-core/src/base64.ts
|
|
108
|
+
/** Estimates decoded bytes without allocating a cleaned copy of the base64 payload. */
|
|
109
|
+
function estimateBase64DecodedBytes(base64) {
|
|
110
|
+
let effectiveLen = 0;
|
|
111
|
+
for (let i = 0; i < base64.length; i += 1) {
|
|
112
|
+
if (base64.charCodeAt(i) <= 32) continue;
|
|
113
|
+
effectiveLen += 1;
|
|
114
|
+
}
|
|
115
|
+
if (effectiveLen === 0) return 0;
|
|
116
|
+
let padding = 0;
|
|
117
|
+
let end = base64.length - 1;
|
|
118
|
+
while (end >= 0 && base64.charCodeAt(end) <= 32) end -= 1;
|
|
119
|
+
if (end >= 0 && base64[end] === "=") {
|
|
120
|
+
padding = 1;
|
|
121
|
+
end -= 1;
|
|
122
|
+
while (end >= 0 && base64.charCodeAt(end) <= 32) end -= 1;
|
|
123
|
+
if (end >= 0 && base64[end] === "=") padding = 2;
|
|
124
|
+
}
|
|
125
|
+
const estimated = Math.floor(effectiveLen * 3 / 4) - padding;
|
|
126
|
+
return Math.max(0, estimated);
|
|
127
|
+
}
|
|
128
|
+
const CANONICALIZE_BASE64_CHUNK_SIZE = 8192;
|
|
129
|
+
function isBase64DataChar(code) {
|
|
130
|
+
return code >= 65 && code <= 90 || code >= 97 && code <= 122 || code >= 48 && code <= 57 || code === 43 || code === 47;
|
|
131
|
+
}
|
|
132
|
+
function base64DataValue(code) {
|
|
133
|
+
if (code >= 65 && code <= 90) return code - 65;
|
|
134
|
+
if (code >= 97 && code <= 122) return code - 97 + 26;
|
|
135
|
+
if (code >= 48 && code <= 57) return code - 48 + 52;
|
|
136
|
+
return code === 43 ? 62 : 63;
|
|
137
|
+
}
|
|
138
|
+
/**
|
|
139
|
+
* Normalizes and validates a base64 string, returning canonical no-whitespace
|
|
140
|
+
* base64 only when the input has valid alphabet, padding, and length.
|
|
141
|
+
*/
|
|
142
|
+
function canonicalizeBase64(base64) {
|
|
143
|
+
const chunks = [];
|
|
144
|
+
let current = "";
|
|
145
|
+
let cleanedLength = 0;
|
|
146
|
+
let padding = 0;
|
|
147
|
+
let sawPadding = false;
|
|
148
|
+
let lastDataCode = 0;
|
|
149
|
+
const append = (char) => {
|
|
150
|
+
current += char;
|
|
151
|
+
cleanedLength += 1;
|
|
152
|
+
if (current.length >= CANONICALIZE_BASE64_CHUNK_SIZE) {
|
|
153
|
+
chunks.push(current);
|
|
154
|
+
current = "";
|
|
155
|
+
}
|
|
156
|
+
};
|
|
157
|
+
for (let i = 0; i < base64.length; i += 1) {
|
|
158
|
+
const code = base64.charCodeAt(i);
|
|
159
|
+
if (code <= 32) continue;
|
|
160
|
+
if (code === 61) {
|
|
161
|
+
padding += 1;
|
|
162
|
+
if (padding > 2) return;
|
|
163
|
+
sawPadding = true;
|
|
164
|
+
append("=");
|
|
165
|
+
continue;
|
|
166
|
+
}
|
|
167
|
+
if (sawPadding || !isBase64DataChar(code)) return;
|
|
168
|
+
lastDataCode = code;
|
|
169
|
+
append(base64[i] ?? "");
|
|
170
|
+
}
|
|
171
|
+
if (cleanedLength === 0) return;
|
|
172
|
+
const remainder = cleanedLength % 4;
|
|
173
|
+
if (remainder !== 0) {
|
|
174
|
+
if (sawPadding || remainder === 1) return;
|
|
175
|
+
current += "=".repeat(4 - remainder);
|
|
176
|
+
}
|
|
177
|
+
const effectivePadding = remainder === 0 ? padding : 4 - remainder;
|
|
178
|
+
const padBitMask = effectivePadding === 2 ? 15 : effectivePadding === 1 ? 3 : 0;
|
|
179
|
+
if (padBitMask !== 0 && (base64DataValue(lastDataCode) & padBitMask) !== 0) return;
|
|
180
|
+
if (current) chunks.push(current);
|
|
181
|
+
return chunks.join("");
|
|
182
|
+
}
|
|
183
|
+
//#endregion
|
|
184
|
+
//#region packages/ai/src/utils/credential-redaction.ts
|
|
185
|
+
const NON_CREDENTIAL_FIELD_NAMES = /* @__PURE__ */ new Set([
|
|
186
|
+
"passwordfile",
|
|
187
|
+
"tokenbudget",
|
|
188
|
+
"tokencount",
|
|
189
|
+
"tokenfield",
|
|
190
|
+
"tokenlimit",
|
|
191
|
+
"tokens"
|
|
192
|
+
]);
|
|
193
|
+
const CREDENTIAL_FIELD_SUFFIX_RE = /(?:apikey|cookie|credential|passphrase|passwd|password|privatekey|secret|secret(?:access)?key|signingkey|token)$/u;
|
|
194
|
+
const MEDIA_PAYLOAD_SUFFIXES = "base64|blob|buffer|bytes|data|delta|frames?|output|result|(?:file|media|source)?(?:uri|url)";
|
|
195
|
+
const MEDIA_FIELD_NAME_RE = new RegExp(`^(?:input|output)?(?:audio|image|video)s?(?:${MEDIA_PAYLOAD_SUFFIXES})*$`, "u");
|
|
196
|
+
const MEDIA_PAYLOAD_SUFFIX_RE = new RegExp(`^(?:${MEDIA_PAYLOAD_SUFFIXES})$`, "u");
|
|
197
|
+
const MEDIA_WRAPPER_NAME_RE = /^(?:input_|output_)?(?:audio|image|video)s?(?:_|$)/iu;
|
|
198
|
+
const AUTHORIZATION_VALUE_RE = /\b(Bearer|Basic)\s+[A-Za-z0-9+/._~=-]{8,}/giu;
|
|
199
|
+
const JWT_VALUE_RE = /\beyJ[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}\b/gu;
|
|
200
|
+
const COOKIE_HEADER_RE = /\b((?:set-)?cookie\s*:\s*)([^\r\n]+)/giu;
|
|
201
|
+
const QUOTED_CREDENTIAL_HEADER_RE = /(["'])((?:[A-Za-z][A-Za-z0-9_.-]*[_.-])?(?:api[_.-]?key|authorization|passphrase|passwd|password|private[_.-]?key|secret(?:[_.-]?access)?[_.-]?key|signing[_.-]?key|token))\1\s*:\s*([^,}\r\n]+)/giu;
|
|
202
|
+
const CREDENTIAL_HEADER_RE = /\b((?:[A-Za-z][A-Za-z0-9_.-]*[_.-])?(?:api[_.-]?key|authorization|passphrase|passwd|password|private[_.-]?key|secret(?:[_.-]?access)?[_.-]?key|signing[_.-]?key|token))\s*:\s*([^\r\n]+)/giu;
|
|
203
|
+
const LOOSE_QUOTED_CREDENTIAL_PAIR_RE = /\b((?!(?:api|endpoint|method|model|provider|status|type)=)[A-Za-z][A-Za-z0-9_.-]{0,64})=(["'])([A-Za-z0-9+/._~%=-]{16,})\2/giu;
|
|
204
|
+
const LOOSE_CREDENTIAL_PAIR_RE = /\b((?!(?:api|endpoint|method|model|provider|status|type)=)[A-Za-z][A-Za-z0-9_.-]{0,64})=([A-Za-z0-9+/._~%=-]{16,})(?=[;&#'"\s]|$)/giu;
|
|
205
|
+
const MEDIA_DATA_URL_RE = /data:(?:audio|image|video)\/[a-z0-9.+-]+(?:;[^,;\s]+)*;base64,[ \t]*(?:\r?\n[ \t]*)?[a-z0-9+/_=-]+(?:[ \t]*\r?\n[ \t]*[a-z0-9+/_=-]+)*/giu;
|
|
206
|
+
const MAX_DIAGNOSTIC_JSON_LENGTH = 16 * 1024;
|
|
207
|
+
const PLAIN_BRACKET_TAG_RE = /^\[[A-Za-z0-9][A-Za-z0-9 _.-]*\]$/u;
|
|
208
|
+
const JSON_ARRAY_START_RE = /\[\s*(?:[{"\d\]-]|true\b|false\b|null\b)/u;
|
|
209
|
+
const MALFORMED_JSON_RE = /\{|(?:"[^"]+"|\b(?:b64_json|data|(?:input|output)?(?:audio|image|video)[\w-]*))\s*:/iu;
|
|
210
|
+
function looksLikeDiagnosticJson(value) {
|
|
211
|
+
return JSON_ARRAY_START_RE.test(value) || MALFORMED_JSON_RE.test(value);
|
|
212
|
+
}
|
|
213
|
+
function normalizeDiagnosticFieldName(value) {
|
|
214
|
+
return value.toLowerCase().replaceAll(/[^a-z0-9]/g, "");
|
|
215
|
+
}
|
|
216
|
+
function isCredentialFieldName(key) {
|
|
217
|
+
const normalized = normalizeDiagnosticFieldName(key);
|
|
218
|
+
if (!normalized || NON_CREDENTIAL_FIELD_NAMES.has(normalized)) return false;
|
|
219
|
+
return normalized === "authorization" || normalized === "proxyauthorization" || CREDENTIAL_FIELD_SUFFIX_RE.test(normalized);
|
|
220
|
+
}
|
|
221
|
+
function redactCredentialText(value) {
|
|
222
|
+
return value.replace(AUTHORIZATION_VALUE_RE, "$1 <redacted>").replace(JWT_VALUE_RE, "<redacted-jwt>").replace(COOKIE_HEADER_RE, "$1<redacted>").replace(QUOTED_CREDENTIAL_HEADER_RE, "$1$2$1: <redacted>").replace(CREDENTIAL_HEADER_RE, "$1: <redacted>").replace(LOOSE_QUOTED_CREDENTIAL_PAIR_RE, "$1=$2<redacted>$2").replace(LOOSE_CREDENTIAL_PAIR_RE, "$1=<redacted>");
|
|
223
|
+
}
|
|
224
|
+
function diagnosticBytes(value, numericArrays = false) {
|
|
225
|
+
return value instanceof ArrayBuffer ? new Uint8Array(value) : ArrayBuffer.isView(value) ? new Uint8Array(value.buffer, value.byteOffset, value.byteLength) : numericArrays && Array.isArray(value) && value.every((byte) => Number.isInteger(byte) && byte >= 0 && byte <= 255) ? Uint8Array.from(value) : void 0;
|
|
226
|
+
}
|
|
227
|
+
function isDiagnosticMediaPayload(descriptors) {
|
|
228
|
+
const type = descriptors.type?.value;
|
|
229
|
+
return typeof type === "string" && /^(?:input|output)?(?:audio|image|video)/u.test(normalizeDiagnosticFieldName(type)) || [
|
|
230
|
+
"mimeType",
|
|
231
|
+
"mime_type",
|
|
232
|
+
"mediaType",
|
|
233
|
+
"media_type",
|
|
234
|
+
"contentType",
|
|
235
|
+
"content_type"
|
|
236
|
+
].some((key) => {
|
|
237
|
+
const mime = descriptors[key]?.value;
|
|
238
|
+
return typeof mime === "string" && /^(?:audio|image|video)\//iu.test(mime);
|
|
239
|
+
});
|
|
240
|
+
}
|
|
241
|
+
function extractDiagnosticMediaField(key, value, parentMedia) {
|
|
242
|
+
const normalized = normalizeDiagnosticFieldName(key);
|
|
243
|
+
const privateField = normalized === "b64json";
|
|
244
|
+
const mediaField = MEDIA_FIELD_NAME_RE.test(normalized) || MEDIA_WRAPPER_NAME_RE.test(key);
|
|
245
|
+
const contextualPayload = parentMedia && MEDIA_PAYLOAD_SUFFIX_RE.test(normalized);
|
|
246
|
+
if (!privateField && !mediaField && !contextualPayload) {
|
|
247
|
+
const nestedMedia = value !== null && (typeof value === "object" || /^(?:0|[1-9]\d*)$/u.test(key));
|
|
248
|
+
return parentMedia && nestedMedia ? { kind: "context" } : void 0;
|
|
249
|
+
}
|
|
250
|
+
if (/(?:uri|url)$/u.test(normalized)) return { kind: "redacted" };
|
|
251
|
+
const encoded = diagnosticBytes(value, true) ?? (typeof value === "string" ? value : void 0);
|
|
252
|
+
if (encoded === void 0) return { kind: privateField || Array.isArray(value) ? "redacted" : "context" };
|
|
253
|
+
return {
|
|
254
|
+
kind: "redacted",
|
|
255
|
+
bytes: typeof encoded === "string" ? estimateBase64DecodedBytes(encoded) : encoded.byteLength,
|
|
256
|
+
source: encoded
|
|
257
|
+
};
|
|
258
|
+
}
|
|
259
|
+
function projectDiagnosticValue(value, policy = {}, seen = /* @__PURE__ */ new WeakSet(), mediaPayload = false, state = {
|
|
260
|
+
changed: false,
|
|
261
|
+
nodesRemaining: 64
|
|
262
|
+
}) {
|
|
263
|
+
try {
|
|
264
|
+
if (typeof value === "string") {
|
|
265
|
+
const projected = redactDiagnosticText(value);
|
|
266
|
+
state.changed ||= projected !== value;
|
|
267
|
+
return projected;
|
|
268
|
+
}
|
|
269
|
+
if (!value || typeof value !== "object") return value;
|
|
270
|
+
const binary = diagnosticBytes(value);
|
|
271
|
+
if (binary) {
|
|
272
|
+
state.changed = true;
|
|
273
|
+
return policy.projectBinary?.(binary) ?? {
|
|
274
|
+
redacted: "<redacted>",
|
|
275
|
+
bytes: binary.byteLength
|
|
276
|
+
};
|
|
277
|
+
}
|
|
278
|
+
if (seen.has(value)) return "[Circular]";
|
|
279
|
+
if (state.nodesRemaining-- <= 0) {
|
|
280
|
+
state.changed = true;
|
|
281
|
+
return "[Truncated]";
|
|
282
|
+
}
|
|
283
|
+
const keys = Reflect.ownKeys(value).slice(0, 65);
|
|
284
|
+
const descriptors = Object.fromEntries(keys.slice(0, 64).flatMap((key) => {
|
|
285
|
+
const descriptor = typeof key === "string" && Object.getOwnPropertyDescriptor(value, key);
|
|
286
|
+
return descriptor ? [[key, descriptor]] : [];
|
|
287
|
+
}));
|
|
288
|
+
state.changed ||= keys.length > 64;
|
|
289
|
+
seen.add(value);
|
|
290
|
+
const out = Array.isArray(value) ? [] : {};
|
|
291
|
+
const rawName = typeof descriptors.name?.value === "string" ? descriptors.name.value : descriptors.key?.value;
|
|
292
|
+
const redactValueField = keys.length > 64 || typeof rawName === "string" && isCredentialFieldName(rawName);
|
|
293
|
+
const redactMedia = mediaPayload || keys.length > 64 || isDiagnosticMediaPayload(descriptors);
|
|
294
|
+
for (const [key, descriptor] of Object.entries(descriptors)) {
|
|
295
|
+
if (!("value" in descriptor) || !descriptor.enumerable && (policy.propertyScope === "enumerable" || ![
|
|
296
|
+
"cause",
|
|
297
|
+
"message",
|
|
298
|
+
"name",
|
|
299
|
+
"stack"
|
|
300
|
+
].includes(key)) || key === "length") continue;
|
|
301
|
+
const child = descriptor.value;
|
|
302
|
+
if (policy.omitField?.(key) || isCredentialFieldName(key)) {
|
|
303
|
+
state.changed = true;
|
|
304
|
+
continue;
|
|
305
|
+
}
|
|
306
|
+
if (redactValueField && key === "value") {
|
|
307
|
+
out[key] = "<redacted>";
|
|
308
|
+
state.changed = true;
|
|
309
|
+
continue;
|
|
310
|
+
}
|
|
311
|
+
const media = extractDiagnosticMediaField(key, child, redactMedia);
|
|
312
|
+
if (media?.kind === "redacted") {
|
|
313
|
+
const redacted = media.bytes === void 0 ? "<redacted>" : {
|
|
314
|
+
redacted: "<redacted>",
|
|
315
|
+
bytes: media.bytes
|
|
316
|
+
};
|
|
317
|
+
Object.assign(out, policy.projectMedia?.(key, media) ?? { [key]: redacted });
|
|
318
|
+
state.changed = true;
|
|
319
|
+
continue;
|
|
320
|
+
}
|
|
321
|
+
out[key] = projectDiagnosticValue(child, policy, seen, media?.kind === "context", state);
|
|
322
|
+
}
|
|
323
|
+
return out;
|
|
324
|
+
} catch {
|
|
325
|
+
state.changed = true;
|
|
326
|
+
return "[Unserializable]";
|
|
327
|
+
}
|
|
328
|
+
}
|
|
329
|
+
/** Redacts bounded structured JSON while preserving harmless diagnostic text byte-for-byte. */
|
|
330
|
+
function redactDiagnosticText(value) {
|
|
331
|
+
const text = redactCredentialText(value).replace(MEDIA_DATA_URL_RE, "<redacted>");
|
|
332
|
+
if (!looksLikeDiagnosticJson(text)) return text;
|
|
333
|
+
if (text.length > MAX_DIAGNOSTIC_JSON_LENGTH) return "[Oversized diagnostic JSON redacted]";
|
|
334
|
+
let cursor = 0;
|
|
335
|
+
let redacted = "";
|
|
336
|
+
let unstructured = "";
|
|
337
|
+
for (const fragment of extractBalancedJsonFragments(text)) {
|
|
338
|
+
const plainText = text.slice(cursor, fragment.startIndex);
|
|
339
|
+
unstructured += plainText;
|
|
340
|
+
redacted += plainText;
|
|
341
|
+
try {
|
|
342
|
+
const state = {
|
|
343
|
+
changed: false,
|
|
344
|
+
nodesRemaining: 64
|
|
345
|
+
};
|
|
346
|
+
const projected = projectDiagnosticValue(JSON.parse(fragment.json), {}, /* @__PURE__ */ new WeakSet(), false, state);
|
|
347
|
+
redacted += state.changed ? stableStringify(projected) : fragment.json;
|
|
348
|
+
} catch {
|
|
349
|
+
if (!PLAIN_BRACKET_TAG_RE.test(fragment.json) || JSON_ARRAY_START_RE.test(fragment.json)) return "[Malformed diagnostic JSON redacted]";
|
|
350
|
+
redacted += fragment.json;
|
|
351
|
+
}
|
|
352
|
+
cursor = fragment.endIndex + 1;
|
|
353
|
+
}
|
|
354
|
+
const remainder = text.slice(cursor);
|
|
355
|
+
return looksLikeDiagnosticJson(unstructured + remainder) ? "[Malformed diagnostic JSON redacted]" : redacted + remainder;
|
|
356
|
+
}
|
|
357
|
+
//#endregion
|
|
358
|
+
//#region packages/ai/src/utils/provider-error.ts
|
|
359
|
+
const MAX_ERROR_BODY_LENGTH = 4e3;
|
|
360
|
+
let providerErrorRedactor;
|
|
361
|
+
function configureProviderErrorRedactor(redactor) {
|
|
362
|
+
const previous = providerErrorRedactor;
|
|
363
|
+
providerErrorRedactor = redactor;
|
|
364
|
+
return previous;
|
|
365
|
+
}
|
|
366
|
+
function readProviderErrorField(record, key) {
|
|
367
|
+
const value = record?.[key];
|
|
368
|
+
return typeof value === "string" || typeof value === "number" && Number.isFinite(value) ? normalizeStringifiedOptionalString(value) : void 0;
|
|
369
|
+
}
|
|
370
|
+
function readCauseCode(error) {
|
|
371
|
+
const seen = /* @__PURE__ */ new Set();
|
|
372
|
+
for (let cause = asOptionalRecord(error.cause); cause && seen.size < 8 && !seen.has(cause); cause = asOptionalRecord(cause.cause)) {
|
|
373
|
+
seen.add(cause);
|
|
374
|
+
const code = readProviderErrorField(cause, "code");
|
|
375
|
+
if (code) return code;
|
|
376
|
+
}
|
|
377
|
+
}
|
|
378
|
+
function stringifyField(value, maxLength) {
|
|
379
|
+
if (value === void 0 || value === null) return;
|
|
380
|
+
const text = redactDiagnosticText((typeof value === "string" ? value : stableStringify(value)).trim());
|
|
381
|
+
if (!text) return;
|
|
382
|
+
return text.length <= maxLength ? text : `${truncateUtf16Safe(text, maxLength)}... [truncated]`;
|
|
383
|
+
}
|
|
384
|
+
function buildProjection(snapshot, signal) {
|
|
385
|
+
const error = asOptionalRecord(snapshot);
|
|
386
|
+
const nestedError = asOptionalRecord(error?.error);
|
|
387
|
+
const response = asOptionalRecord(error?.response);
|
|
388
|
+
const status = [
|
|
389
|
+
error?.status,
|
|
390
|
+
error?.statusCode,
|
|
391
|
+
response?.status,
|
|
392
|
+
response?.statusCode
|
|
393
|
+
].find((value) => typeof value === "number" && Number.isFinite(value));
|
|
394
|
+
const bodyValue = error?.errorBody ?? error?.body ?? response?.body ?? response?.data ?? nestedError;
|
|
395
|
+
const body = stringifyField(bodyValue, MAX_ERROR_BODY_LENGTH);
|
|
396
|
+
const originalMessage = (typeof snapshot === "string" ? snapshot : void 0) ?? readProviderErrorField(error, "message") ?? readProviderErrorField(nestedError, "message");
|
|
397
|
+
const genericMessage = originalMessage === `${status} status code (no body)`;
|
|
398
|
+
let errorMessage = status !== void 0 && body && (!originalMessage || genericMessage) ? `${status}: ${body}` : originalMessage ?? body ?? stringifyField(snapshot, MAX_ERROR_BODY_LENGTH) ?? "Unknown provider error";
|
|
399
|
+
if (status !== void 0 && !body && originalMessage && !originalMessage.startsWith(String(status))) errorMessage = `${status}: ${errorMessage}`;
|
|
400
|
+
const rawMetadata = stringifyField(asOptionalRecord(nestedError?.metadata)?.raw, MAX_ERROR_BODY_LENGTH);
|
|
401
|
+
if (rawMetadata && !errorMessage.includes(rawMetadata)) errorMessage += `\n${rawMetadata}`;
|
|
402
|
+
const errorCode = readProviderErrorField(error, "errorCode") ?? readProviderErrorField(error, "code") ?? readProviderErrorField(nestedError, "code") ?? (error ? readCauseCode(error) : void 0) ?? (status === void 0 ? void 0 : String(status));
|
|
403
|
+
const errorType = readProviderErrorField(error, "errorType") ?? readProviderErrorField(error, "type") ?? readProviderErrorField(nestedError, "type");
|
|
404
|
+
return {
|
|
405
|
+
stopReason: signal?.aborted ? "aborted" : "error",
|
|
406
|
+
errorMessage: stringifyField(errorMessage, 4096) ?? "Unknown provider error",
|
|
407
|
+
...errorCode ? { errorCode: truncateUtf16Safe(errorCode, 256) } : {},
|
|
408
|
+
...errorType ? { errorType: truncateUtf16Safe(errorType, 256) } : {},
|
|
409
|
+
...body ? { errorBody: stringifyField(bodyValue, 500) } : {}
|
|
410
|
+
};
|
|
411
|
+
}
|
|
412
|
+
/** Projects one hostile provider throw into final, bounded assistant terminal fields. */
|
|
413
|
+
function projectProviderError(error, signal) {
|
|
414
|
+
try {
|
|
415
|
+
const localSnapshot = projectDiagnosticValue(error);
|
|
416
|
+
let snapshot = localSnapshot;
|
|
417
|
+
try {
|
|
418
|
+
snapshot = providerErrorRedactor?.(localSnapshot) ?? localSnapshot;
|
|
419
|
+
} catch {}
|
|
420
|
+
return buildProjection(snapshot, signal);
|
|
421
|
+
} catch {
|
|
422
|
+
return {
|
|
423
|
+
stopReason: signal?.aborted ? "aborted" : "error",
|
|
424
|
+
errorMessage: "Unknown provider error"
|
|
425
|
+
};
|
|
426
|
+
}
|
|
427
|
+
}
|
|
428
|
+
//#endregion
|
|
429
|
+
export { estimateBase64DecodedBytes as a, canonicalizeBase64 as i, projectProviderError as n, stableStringify as o, projectDiagnosticValue as r, configureProviderErrorRedactor as t };
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
//#region packages/ai/src/utils/provider-error.d.ts
|
|
2
|
+
type ProviderErrorProjection = {
|
|
3
|
+
stopReason: "aborted" | "error";
|
|
4
|
+
errorMessage: string;
|
|
5
|
+
errorCode?: string;
|
|
6
|
+
errorType?: string;
|
|
7
|
+
errorBody?: string;
|
|
8
|
+
};
|
|
9
|
+
type ProviderErrorRedactor = (value: unknown) => unknown;
|
|
10
|
+
declare function configureProviderErrorRedactor(redactor: ProviderErrorRedactor | undefined): ProviderErrorRedactor | undefined;
|
|
11
|
+
//#endregion
|
|
12
|
+
export { ProviderErrorRedactor as n, configureProviderErrorRedactor as r, ProviderErrorProjection as t };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { H as StreamOptions } from "./types-BHNrPS1l.mjs";
|
|
2
2
|
import OpenAI from "openai";
|
|
3
3
|
import Anthropic from "@anthropic-ai/sdk";
|
|
4
4
|
import { ResponseCreateParamsStreaming } from "openai/resources/responses/responses.js";
|
|
@@ -73,6 +73,10 @@ declare function reconcileOpenAIResponsesToolChoice(choice: OpenAIResponsesToolC
|
|
|
73
73
|
declare function reconcileOpenAICompletionsToolChoice(choice: OpenAICompletionsSdkToolChoice, projection: OpenAIToolProjection): OpenAICompletionsSdkToolChoice | undefined;
|
|
74
74
|
//#endregion
|
|
75
75
|
//#region packages/ai/src/provider-options.d.ts
|
|
76
|
+
type OpenAIResponsesCompactionRejection = {
|
|
77
|
+
data: string;
|
|
78
|
+
id?: string;
|
|
79
|
+
};
|
|
76
80
|
type AnthropicEffort = "low" | "medium" | "high" | "xhigh" | "max";
|
|
77
81
|
type AnthropicThinkingDisplay = "summarized" | "omitted";
|
|
78
82
|
/** Provider options shared by the Anthropic provider and canonical transport. */
|
|
@@ -128,8 +132,10 @@ type BaseOpenAIStreamOptions = StreamOptions & {
|
|
|
128
132
|
topP?: number;
|
|
129
133
|
authProfileId?: string;
|
|
130
134
|
firstEventTimeoutMs?: number;
|
|
131
|
-
onFirstEventTimeout?: (reason: Error) => void;
|
|
135
|
+
onFirstEventTimeout?: (reason: Error) => void; /** Internal owner notification after a server rejects a persisted compaction checkpoint. */
|
|
136
|
+
onCompactionRejected?: (checkpoint: OpenAIResponsesCompactionRejection) => void;
|
|
132
137
|
openclawCodeModeToolSurface?: boolean;
|
|
138
|
+
openclawCodeModeAllowedHostedToolTypes?: Set<string>;
|
|
133
139
|
frequencyPenalty?: number;
|
|
134
140
|
presencePenalty?: number;
|
|
135
141
|
seed?: number;
|
|
@@ -141,4 +147,4 @@ type OpenAICompletionsOptions = BaseOpenAIStreamOptions & {
|
|
|
141
147
|
reasoningEffort?: OpenAIReasoningEffort;
|
|
142
148
|
};
|
|
143
149
|
//#endregion
|
|
144
|
-
export {
|
|
150
|
+
export { normalizeOpenAIReasoningEffort as _, OpenAICompletionsOptions as a, supportsOpenAIReasoningEffort as b, OpenAIToolProjection as c, reconcileOpenAIResponsesToolChoice as d, OpenAIApiReasoningEffort as f, isOpenAIGpt56Model as g, isOpenAIGpt55Model as h, BaseOpenAIStreamOptions as i, projectOpenAITools as l, isOpenAIGpt54MiniModel as m, AnthropicOptions as n, OpenAIResponsesCompactionRejection as o, OpenAIReasoningEffort as p, AnthropicThinkingDisplay as r, OpenAICompletionsToolChoice as s, AnthropicEffort as t, reconcileOpenAICompletionsToolChoice as u, resolveOpenAIReasoningEffortForModel as v, supportsOpenAITemperature as x, resolveOpenAISupportedReasoningEfforts as y };
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import { r as createAssistantMessageEventStream } from "./event-stream-uSMZJ3FA.mjs";
|
|
2
|
+
import { t as sanitizeSurrogates } from "./sanitize-unicode-BYqrYtC_.mjs";
|
|
3
|
+
import { i as transformMessages } from "./host-DTqNc7ad.mjs";
|
|
4
|
+
import { i as asOptionalRecord, t as asNonArrayRecord } from "./record-coerce-DdXsgUd_.mjs";
|
|
5
|
+
import { n as projectProviderError } from "./provider-error-BUwEnjXq.mjs";
|
|
6
|
+
//#region packages/ai/src/transports/transport-stream-shared.ts
|
|
7
|
+
const EMPTY_TOOL_RESULT_TEXT = "(no output)";
|
|
8
|
+
function sanitizeTransportPayloadText(text) {
|
|
9
|
+
if (typeof text !== "string") return "";
|
|
10
|
+
return sanitizeSurrogates(text);
|
|
11
|
+
}
|
|
12
|
+
function sanitizeNonEmptyTransportPayloadText(text, fallback = EMPTY_TOOL_RESULT_TEXT) {
|
|
13
|
+
const sanitized = sanitizeTransportPayloadText(text);
|
|
14
|
+
return sanitized.trim().length > 0 ? sanitized : fallback;
|
|
15
|
+
}
|
|
16
|
+
function coerceTransportToolCallArguments(argumentsValue) {
|
|
17
|
+
const argumentsRecord = asOptionalRecord(argumentsValue);
|
|
18
|
+
if (argumentsRecord) return argumentsRecord;
|
|
19
|
+
if (typeof argumentsValue === "string") try {
|
|
20
|
+
return asNonArrayRecord(JSON.parse(argumentsValue));
|
|
21
|
+
} catch {}
|
|
22
|
+
return {};
|
|
23
|
+
}
|
|
24
|
+
function mergeTransportHeaders(...headerSources) {
|
|
25
|
+
const merged = {};
|
|
26
|
+
for (const headers of headerSources) if (headers) Object.assign(merged, headers);
|
|
27
|
+
return Object.keys(merged).length > 0 ? merged : void 0;
|
|
28
|
+
}
|
|
29
|
+
function mergeTransportMetadata(payload, metadata) {
|
|
30
|
+
if (!metadata || Object.keys(metadata).length === 0) return payload;
|
|
31
|
+
const existingMetadata = asOptionalRecord(payload.metadata);
|
|
32
|
+
return {
|
|
33
|
+
...payload,
|
|
34
|
+
metadata: {
|
|
35
|
+
...existingMetadata,
|
|
36
|
+
...metadata
|
|
37
|
+
}
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
function createEmptyTransportUsage() {
|
|
41
|
+
return {
|
|
42
|
+
input: 0,
|
|
43
|
+
output: 0,
|
|
44
|
+
cacheRead: 0,
|
|
45
|
+
cacheWrite: 0,
|
|
46
|
+
totalTokens: 0,
|
|
47
|
+
cost: {
|
|
48
|
+
input: 0,
|
|
49
|
+
output: 0,
|
|
50
|
+
cacheRead: 0,
|
|
51
|
+
cacheWrite: 0,
|
|
52
|
+
total: 0
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
}
|
|
56
|
+
function createWritableTransportEventStream() {
|
|
57
|
+
const eventStream = createAssistantMessageEventStream();
|
|
58
|
+
return {
|
|
59
|
+
eventStream,
|
|
60
|
+
stream: eventStream
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Abort error to surface for an aborted `signal`.
|
|
65
|
+
*
|
|
66
|
+
* Rethrows the caller's abort reason only when it carries a `code`, so that code
|
|
67
|
+
* survives into `errorCode` on the persisted assistant message and consumers can
|
|
68
|
+
* recognize an abort's origin without matching error text. A default
|
|
69
|
+
* `abort()` reason is an uncoded DOMException that carries nothing the synthetic
|
|
70
|
+
* error does not, so it keeps the "Request was aborted" text every transport
|
|
71
|
+
* already emits rather than churning it.
|
|
72
|
+
*/
|
|
73
|
+
function transportAbortError(signal) {
|
|
74
|
+
const reason = signal?.reason;
|
|
75
|
+
return reason instanceof Error && typeof reason.code === "string" ? reason : /* @__PURE__ */ new Error("Request was aborted");
|
|
76
|
+
}
|
|
77
|
+
/** Run a provider-response hook before start/body consumption inside the first-event deadline. */
|
|
78
|
+
function withProviderResponseHook(params) {
|
|
79
|
+
return { async *[Symbol.asyncIterator]() {
|
|
80
|
+
let onAbort;
|
|
81
|
+
try {
|
|
82
|
+
if (params.signal.aborted) throw transportAbortError(params.signal);
|
|
83
|
+
if (params.hook) await Promise.race([Promise.resolve().then(params.hook), new Promise((_resolve, reject) => {
|
|
84
|
+
onAbort = () => reject(transportAbortError(params.signal));
|
|
85
|
+
params.signal.addEventListener("abort", onAbort, { once: true });
|
|
86
|
+
})]);
|
|
87
|
+
} catch (error) {
|
|
88
|
+
params.abort(error instanceof Error ? error : new Error(String(error)));
|
|
89
|
+
throw error;
|
|
90
|
+
} finally {
|
|
91
|
+
if (onAbort) params.signal.removeEventListener("abort", onAbort);
|
|
92
|
+
}
|
|
93
|
+
if (params.signal.aborted) throw transportAbortError(params.signal);
|
|
94
|
+
params.onReady?.();
|
|
95
|
+
if (params.stream) yield* params.stream;
|
|
96
|
+
} };
|
|
97
|
+
}
|
|
98
|
+
function finalizeTransportStream(params) {
|
|
99
|
+
const { stream, output, signal } = params;
|
|
100
|
+
if (signal?.aborted) throw transportAbortError(signal);
|
|
101
|
+
if (output.stopReason === "aborted" || output.stopReason === "error") throw new Error(output.errorMessage ?? "An unknown error occurred");
|
|
102
|
+
stream.push({
|
|
103
|
+
type: "done",
|
|
104
|
+
reason: output.stopReason,
|
|
105
|
+
message: output
|
|
106
|
+
});
|
|
107
|
+
stream.end();
|
|
108
|
+
}
|
|
109
|
+
/** @deprecated Use projectProviderError. v2026.7.2-beta.5 compatibility; remove after 2026.10. */
|
|
110
|
+
function assignTransportErrorDetails(output, error, signal) {
|
|
111
|
+
Object.assign(output, projectProviderError(error, signal));
|
|
112
|
+
}
|
|
113
|
+
function failTransportStream(params) {
|
|
114
|
+
const { stream, output, signal, error, cleanup } = params;
|
|
115
|
+
cleanup?.();
|
|
116
|
+
assignTransportErrorDetails(output, error, signal);
|
|
117
|
+
stream.push({
|
|
118
|
+
type: "error",
|
|
119
|
+
reason: output.stopReason,
|
|
120
|
+
error: output
|
|
121
|
+
});
|
|
122
|
+
stream.end();
|
|
123
|
+
}
|
|
124
|
+
//#endregion
|
|
125
|
+
//#region packages/ai/src/provider-transcript-transform.ts
|
|
126
|
+
const IMAGE_OMISSION = "(image omitted: model does not support images)";
|
|
127
|
+
const VIDEO_OMISSION = "(video omitted: provider does not support video input)";
|
|
128
|
+
function projectUserMediaForTransport(content, supportsImages, supportsVideo) {
|
|
129
|
+
const result = [];
|
|
130
|
+
for (const block of content) {
|
|
131
|
+
if (block.type === "text" || block.type === "image" && supportsImages || block.type === "video" && supportsVideo) {
|
|
132
|
+
result.push(block);
|
|
133
|
+
continue;
|
|
134
|
+
}
|
|
135
|
+
const text = block.type === "video" ? VIDEO_OMISSION : IMAGE_OMISSION;
|
|
136
|
+
const previous = result.at(-1);
|
|
137
|
+
if (block.data.trim() && !(previous?.type === "text" && previous.text === text)) result.push({
|
|
138
|
+
type: "text",
|
|
139
|
+
text
|
|
140
|
+
});
|
|
141
|
+
}
|
|
142
|
+
return result;
|
|
143
|
+
}
|
|
144
|
+
function transformProviderMessages(messages, model, normalizeToolCallId) {
|
|
145
|
+
const target = {
|
|
146
|
+
...model,
|
|
147
|
+
input: model.input.filter((type) => type !== "video")
|
|
148
|
+
};
|
|
149
|
+
return transformMessages(messages.map((message) => {
|
|
150
|
+
if (message.role !== "user" || !Array.isArray(message.content)) return message;
|
|
151
|
+
return Object.assign({}, message, { content: projectUserMediaForTransport(message.content, model.input.includes("image"), model.api === "openai-completions" && model.input.includes("video")) });
|
|
152
|
+
}), target, normalizeToolCallId);
|
|
153
|
+
}
|
|
154
|
+
//#endregion
|
|
155
|
+
export { createWritableTransportEventStream as a, mergeTransportHeaders as c, sanitizeTransportPayloadText as d, transportAbortError as f, createEmptyTransportUsage as i, mergeTransportMetadata as l, assignTransportErrorDetails as n, failTransportStream as o, withProviderResponseHook as p, coerceTransportToolCallArguments as r, finalizeTransportStream as s, transformProviderMessages as t, sanitizeNonEmptyTransportPayloadText as u };
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { a as requiresClaudeMandatoryAdaptiveThinking, c as resolveClaudeMythos5ModelIdentity, d as resolveClaudeSonnet5ModelIdentity, f as supportsClaude1MContext, g as supportsClaudeNativeXhighEffort, h as supportsClaudeNativeMaxEffort, i as requiresClaudeDefaultSampling, l as resolveClaudeNativeThinkingLevelMap, m as supportsClaudeFastMode, n as CLAUDE_OPUS_5_THINKING_PROFILE, o as resolveClaudeFable5ModelIdentity, p as supportsClaudeAdaptiveThinking, r as CLAUDE_SONNET_5_THINKING_PROFILE, s as resolveClaudeModelIdentity, t as CLAUDE_FABLE_5_THINKING_PROFILE, u as resolveClaudeOpus5ModelIdentity } from "./anthropic-SrGtwsJu.mjs";
|
|
2
|
+
import { a as extractDiagnosticError, i as createAssistantMessageDiagnostic, n as DiagnosticErrorInfo, o as formatThrownValue, r as appendAssistantMessageDiagnostic, t as AssistantMessageDiagnostic } from "./diagnostics-BaTA9eVl.mjs";
|
|
3
|
+
import { $ as Usage, A as OpenRouterRouting, B as StreamFn, C as KnownImagesProvider, D as ModelThinkingLevel, E as Model, F as ProviderReplayState, G as ThinkingBudgets, H as StreamOptions, I as ProviderResponse, J as ThinkingLevelMap, K as ThinkingContent, M as PROVIDER_POST_DISPATCH_AMBIGUITY_ERROR_CODE, N as Provider, O as OpenAICompletionsCompat, P as ProviderImagesOptions, Q as Transport, R as SimpleStreamOptions, S as KnownImagesApi, U as TextContent, W as TextSignatureV1, X as ToolCall, Y as Tool, Z as ToolResultMessage, _ as ImagesOptions, a as AssistantMessageEvent, b as ImagesStopReason, c as CacheRetention, d as ImageContent, et as UserMessage, f as ImagesApi, g as ImagesModel, h as ImagesInputContent, i as AssistantMessage, j as PROVIDER_FAILURE_WITH_OUTPUT_ERROR_CODE, k as OpenAIResponsesCompat, l as CompleteSimpleFn, m as ImagesFunction, n as Api, nt as VercelGatewayRouting, o as AssistantMessageEventStreamContract, p as ImagesContext, q as ThinkingLevel, r as AssistantImages, s as AssistantMessageEventStreamLike, t as AnthropicMessagesCompat, tt as ValidateToolArgumentsFn, u as Context, v as ImagesOutputContent, w as MaybePromise, x as KnownApi, y as ImagesProvider, z as StopReason } from "./types-BHNrPS1l.mjs";
|
|
4
|
+
import { n as EventStream, r as createAssistantMessageEventStream, t as AssistantMessageEventStream } from "./event-stream-BP6AWT8j.mjs";
|
|
5
|
+
import { n as validateToolCall, t as validateToolArguments } from "./validation-DT9SrFn3.mjs";
|
|
6
|
+
//#region packages/ai/src/provider-types.d.ts
|
|
7
|
+
declare const PROVIDER_CONTEXT_HANDOFF: unique symbol;
|
|
8
|
+
type VideoContent = Omit<ImageContent, "type"> & {
|
|
9
|
+
type: "video";
|
|
10
|
+
};
|
|
11
|
+
type MediaContent = ImageContent | VideoContent;
|
|
12
|
+
type ModelInputContent = TextContent | MediaContent;
|
|
13
|
+
type ProviderUserMessage = Omit<UserMessage, "content"> & {
|
|
14
|
+
content: string | ModelInputContent[];
|
|
15
|
+
};
|
|
16
|
+
type ProviderMessage = ProviderUserMessage | AssistantMessage | ToolResultMessage;
|
|
17
|
+
type ProviderContext = Omit<Context, "messages"> & {
|
|
18
|
+
messages: ProviderMessage[];
|
|
19
|
+
};
|
|
20
|
+
type ProviderModel<TApi extends Api = Api> = Omit<Model<TApi>, "input"> & {
|
|
21
|
+
input: ModelInputContent["type"][];
|
|
22
|
+
};
|
|
23
|
+
type ProviderContextHandoff = () => Promise<ProviderContext>;
|
|
24
|
+
type ProviderStreamOptions = StreamOptions & {
|
|
25
|
+
[PROVIDER_CONTEXT_HANDOFF]?: ProviderContextHandoff;
|
|
26
|
+
};
|
|
27
|
+
type ProviderStreamFunction<TApi extends Api = Api, TOptions extends StreamOptions = ProviderStreamOptions> = (model: ProviderModel<TApi>, context: ProviderContext, options?: TOptions) => AssistantMessageEventStreamContract;
|
|
28
|
+
/** Resolves provider-only context without widening the canonical call contract. */
|
|
29
|
+
declare function resolveProviderContext(context: Context | ProviderContext, options?: ProviderStreamOptions): Promise<ProviderContext>;
|
|
30
|
+
//#endregion
|
|
31
|
+
export { type AnthropicMessagesCompat, type Api, type AssistantImages, type AssistantMessage, type AssistantMessageDiagnostic, type AssistantMessageEvent, type AssistantMessageEventStream, type AssistantMessageEventStreamContract, type AssistantMessageEventStreamLike, type CLAUDE_FABLE_5_THINKING_PROFILE, type CLAUDE_OPUS_5_THINKING_PROFILE, type CLAUDE_SONNET_5_THINKING_PROFILE, type CacheRetention, type CompleteSimpleFn, type ProviderContext as Context, ProviderContext, type DiagnosticErrorInfo, type EventStream, type ImageContent, type ImagesApi, type ImagesContext, type ImagesFunction, type ImagesInputContent, type ImagesModel, type ImagesOptions, type ImagesOutputContent, type ImagesProvider, type ImagesStopReason, type KnownApi, type KnownImagesApi, type KnownImagesProvider, type MaybePromise, MediaContent, type ProviderMessage as Message, ProviderMessage, type ProviderModel as Model, ProviderModel, ModelInputContent, type ModelThinkingLevel, type OpenAICompletionsCompat, type OpenAIResponsesCompat, type OpenRouterRouting, PROVIDER_CONTEXT_HANDOFF, type PROVIDER_FAILURE_WITH_OUTPUT_ERROR_CODE, type PROVIDER_POST_DISPATCH_AMBIGUITY_ERROR_CODE, type Provider, ProviderContextHandoff, type ProviderImagesOptions, type ProviderReplayState, type ProviderResponse, ProviderStreamFunction, type ProviderStreamFunction as StreamFunction, ProviderStreamOptions, ProviderUserMessage, type SimpleStreamOptions, type StopReason, type StreamFn, type StreamOptions, type TextContent, type TextSignatureV1, type ThinkingBudgets, type ThinkingContent, type ThinkingLevel, type ThinkingLevelMap, type Tool, type ToolCall, type ToolResultMessage, type Transport, type Usage, type UserMessage, type ValidateToolArgumentsFn, type VercelGatewayRouting, VideoContent, type appendAssistantMessageDiagnostic, type createAssistantMessageDiagnostic, type createAssistantMessageEventStream, type extractDiagnosticError, type formatThrownValue, type requiresClaudeDefaultSampling, type requiresClaudeMandatoryAdaptiveThinking, type resolveClaudeFable5ModelIdentity, type resolveClaudeModelIdentity, type resolveClaudeMythos5ModelIdentity, type resolveClaudeNativeThinkingLevelMap, type resolveClaudeOpus5ModelIdentity, type resolveClaudeSonnet5ModelIdentity, resolveProviderContext, type supportsClaude1MContext, type supportsClaudeAdaptiveThinking, type supportsClaudeFastMode, type supportsClaudeNativeMaxEffort, type supportsClaudeNativeXhighEffort, type validateToolArguments, type validateToolCall };
|