@prestyj/ai 5.10.0 → 5.11.0

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/index.cjs CHANGED
@@ -40,6 +40,7 @@ __export(index_exports, {
40
40
  environmentSecrets: () => environmentSecrets,
41
41
  formatError: () => formatError,
42
42
  formatErrorForDisplay: () => formatErrorForDisplay,
43
+ hasLoneSurrogate: () => hasLoneSurrogate,
43
44
  isHardBillingMessage: () => isHardBillingMessage,
44
45
  isUsageLimitError: () => isUsageLimitError,
45
46
  localWireModelId: () => localWireModelId,
@@ -52,10 +53,14 @@ __export(index_exports, {
52
53
  redactText: () => redactText,
53
54
  redactValue: () => redactValue,
54
55
  registerPalsuProvider: () => registerPalsuProvider,
56
+ sanitizeMessagesForWire: () => sanitizeMessagesForWire,
55
57
  setProviderDiagnostic: () => setProviderDiagnostic,
58
+ sliceHead: () => sliceHead,
59
+ sliceTail: () => sliceTail,
56
60
  stream: () => stream,
57
61
  toAnthropicMessages: () => toAnthropicMessages,
58
- toOpenAIMessages: () => toOpenAIMessages
62
+ toOpenAIMessages: () => toOpenAIMessages,
63
+ toWellFormedText: () => toWellFormedText
59
64
  });
60
65
  module.exports = __toCommonJS(index_exports);
61
66
 
@@ -3380,14 +3385,16 @@ async function* runStream4(options) {
3380
3385
  let thinkingAccum = "";
3381
3386
  let stopReason = "end_turn";
3382
3387
  let inputTokens = 0;
3383
- let outputTokens = 0;
3388
+ let candidateTokens = 0;
3389
+ let reasoningTokens = 0;
3384
3390
  let cacheRead = 0;
3385
3391
  let toolIndex = 0;
3386
3392
  const handleResponse = function* (chunk) {
3387
3393
  const usage = usageFromResponse(chunk);
3388
3394
  if (usage) {
3389
3395
  inputTokens = usage.promptTokenCount ?? inputTokens;
3390
- outputTokens = usage.candidatesTokenCount ?? outputTokens;
3396
+ candidateTokens = usage.candidatesTokenCount ?? candidateTokens;
3397
+ reasoningTokens = usage.thoughtsTokenCount ?? reasoningTokens;
3391
3398
  cacheRead = usage.cachedContentTokenCount ?? cacheRead;
3392
3399
  }
3393
3400
  const reason = finishReasonFromResponse(chunk);
@@ -3443,6 +3450,7 @@ async function* runStream4(options) {
3443
3450
  }
3444
3451
  if (pendingToolCalls.length > 0) stopReason = "tool_use";
3445
3452
  const adjustedInputTokens = Math.max(0, inputTokens - cacheRead);
3453
+ const outputTokens = candidateTokens + reasoningTokens;
3446
3454
  const streamResponse = {
3447
3455
  message: {
3448
3456
  role: "assistant",
@@ -3452,6 +3460,7 @@ async function* runStream4(options) {
3452
3460
  usage: {
3453
3461
  inputTokens: adjustedInputTokens,
3454
3462
  outputTokens,
3463
+ ...reasoningTokens > 0 ? { reasoningTokens } : {},
3455
3464
  ...cacheRead > 0 ? { cacheRead } : {}
3456
3465
  }
3457
3466
  };
@@ -3500,6 +3509,140 @@ var ProviderRegistryImpl = class {
3500
3509
  };
3501
3510
  var providerRegistry = new ProviderRegistryImpl();
3502
3511
 
3512
+ // src/utils/well-formed.ts
3513
+ var LONE_SURROGATE = /[\uD800-\uDBFF](?![\uDC00-\uDFFF])|(?<![\uD800-\uDBFF])[\uDC00-\uDFFF]/;
3514
+ var LONE_SURROGATE_GLOBAL = new RegExp(LONE_SURROGATE, "g");
3515
+ var REPLACEMENT = "\uFFFD";
3516
+ function hasLoneSurrogate(text) {
3517
+ const isWellFormed = text.isWellFormed;
3518
+ if (typeof isWellFormed === "function") return !isWellFormed.call(text);
3519
+ return LONE_SURROGATE.test(text);
3520
+ }
3521
+ function toWellFormedText(text) {
3522
+ if (!hasLoneSurrogate(text)) return text;
3523
+ const toWellFormed = text.toWellFormed;
3524
+ if (typeof toWellFormed === "function") return toWellFormed.call(text);
3525
+ return text.replace(LONE_SURROGATE_GLOBAL, REPLACEMENT);
3526
+ }
3527
+ function isHighSurrogate(code) {
3528
+ return code !== void 0 && code >= 55296 && code <= 56319;
3529
+ }
3530
+ function isLowSurrogate(code) {
3531
+ return code !== void 0 && code >= 56320 && code <= 57343;
3532
+ }
3533
+ function sliceHead(text, chars) {
3534
+ if (chars <= 0) return "";
3535
+ if (chars >= text.length) return text;
3536
+ const end = isHighSurrogate(text.charCodeAt(chars - 1)) ? chars - 1 : chars;
3537
+ return text.slice(0, end);
3538
+ }
3539
+ function sliceTail(text, chars) {
3540
+ if (chars <= 0) return "";
3541
+ if (chars >= text.length) return text;
3542
+ const start = text.length - chars;
3543
+ return text.slice(isLowSurrogate(text.charCodeAt(start)) ? start + 1 : start);
3544
+ }
3545
+ function sanitizeJsonValue(value) {
3546
+ if (typeof value === "string") return toWellFormedText(value);
3547
+ if (Array.isArray(value)) {
3548
+ let changed = false;
3549
+ const next = value.map((item) => {
3550
+ const sanitized = sanitizeJsonValue(item);
3551
+ if (sanitized !== item) changed = true;
3552
+ return sanitized;
3553
+ });
3554
+ return changed ? next : value;
3555
+ }
3556
+ if (value !== null && typeof value === "object") {
3557
+ let changed = false;
3558
+ const next = {};
3559
+ for (const [key, item] of Object.entries(value)) {
3560
+ const sanitizedKey = toWellFormedText(key);
3561
+ const sanitized = sanitizeJsonValue(item);
3562
+ if (sanitizedKey !== key || sanitized !== item) changed = true;
3563
+ next[sanitizedKey] = sanitized;
3564
+ }
3565
+ return changed ? next : value;
3566
+ }
3567
+ return value;
3568
+ }
3569
+ function sanitizeRecord(value) {
3570
+ return sanitizeJsonValue(value);
3571
+ }
3572
+ function sanitizePart(part) {
3573
+ switch (part.type) {
3574
+ case "text":
3575
+ case "thinking": {
3576
+ const text = toWellFormedText(part.text);
3577
+ return text === part.text ? part : { ...part, text };
3578
+ }
3579
+ case "tool_call": {
3580
+ const args = sanitizeRecord(part.args);
3581
+ return args === part.args ? part : { ...part, args };
3582
+ }
3583
+ case "server_tool_call": {
3584
+ const input = sanitizeJsonValue(part.input);
3585
+ return input === part.input ? part : { ...part, input };
3586
+ }
3587
+ case "server_tool_result": {
3588
+ const data = sanitizeJsonValue(part.data);
3589
+ return data === part.data ? part : { ...part, data };
3590
+ }
3591
+ case "raw": {
3592
+ const data = sanitizeRecord(part.data);
3593
+ return data === part.data ? part : { ...part, data };
3594
+ }
3595
+ default:
3596
+ return part;
3597
+ }
3598
+ }
3599
+ function sanitizeParts(parts) {
3600
+ let changed = false;
3601
+ const next = parts.map((part) => {
3602
+ const sanitized = sanitizePart(part);
3603
+ if (sanitized !== part) changed = true;
3604
+ return sanitized;
3605
+ });
3606
+ return changed ? next : parts;
3607
+ }
3608
+ function sanitizeToolResultContent(content) {
3609
+ if (typeof content === "string") return toWellFormedText(content);
3610
+ return sanitizeParts(content);
3611
+ }
3612
+ function sanitizeToolResults(results) {
3613
+ let changed = false;
3614
+ const next = results.map((result) => {
3615
+ const content = sanitizeToolResultContent(result.content);
3616
+ if (content === result.content) return result;
3617
+ changed = true;
3618
+ return { ...result, content };
3619
+ });
3620
+ return changed ? next : results;
3621
+ }
3622
+ function sanitizeMessage(message) {
3623
+ if (message.role === "tool") {
3624
+ const content2 = sanitizeToolResults(message.content);
3625
+ return content2 === message.content ? message : { ...message, content: content2 };
3626
+ }
3627
+ if (typeof message.content === "string") {
3628
+ const content2 = toWellFormedText(message.content);
3629
+ return content2 === message.content ? message : { ...message, content: content2 };
3630
+ }
3631
+ const content = sanitizeParts(message.content);
3632
+ return content === message.content ? message : { ...message, content };
3633
+ }
3634
+ function sanitizeMessagesForWire(messages) {
3635
+ let sanitized;
3636
+ for (let index = 0; index < messages.length; index++) {
3637
+ const message = messages[index];
3638
+ const next = sanitizeMessage(message);
3639
+ if (next === message) continue;
3640
+ sanitized ??= messages.slice();
3641
+ sanitized[index] = next;
3642
+ }
3643
+ return sanitized ?? messages;
3644
+ }
3645
+
3503
3646
  // src/stream.ts
3504
3647
  var GLM_CODING_BASE_URL = "https://api.z.ai/api/coding/paas/v4";
3505
3648
  var KIMI_CODE_USER_AGENT = `kimi-code-cli/${process.env.KIMI_CODE_VERSION ?? "1.0.11"}`;
@@ -3621,13 +3764,25 @@ function stream(options) {
3621
3764
  if (options.supportsVideo !== true && messagesContainVideo(options.messages)) {
3622
3765
  throw new VideoUnsupportedError();
3623
3766
  }
3767
+ const wireMessages = stripMessageProvenance(options.messages);
3624
3768
  const messages = clampProviderContextImages(
3625
- options.messages,
3769
+ sanitizeMessagesForWire(wireMessages),
3626
3770
  options.provider,
3627
3771
  options.supportsImages
3628
3772
  );
3629
3773
  return entry.stream(messages === options.messages ? options : { ...options, messages });
3630
3774
  }
3775
+ function stripMessageProvenance(messages) {
3776
+ let stripped;
3777
+ for (let index = 0; index < messages.length; index++) {
3778
+ const message = messages[index];
3779
+ if (!message.provenance) continue;
3780
+ stripped ??= messages.slice();
3781
+ const { provenance: _provenance, ...wireMessage } = message;
3782
+ stripped[index] = wireMessage;
3783
+ }
3784
+ return stripped ?? messages;
3785
+ }
3631
3786
  function messagesContainVideo(messages) {
3632
3787
  for (const msg of messages) {
3633
3788
  if (typeof msg.content === "string" || !Array.isArray(msg.content)) continue;
@@ -4013,6 +4168,7 @@ function registerPalsuProvider(config) {
4013
4168
  environmentSecrets,
4014
4169
  formatError,
4015
4170
  formatErrorForDisplay,
4171
+ hasLoneSurrogate,
4016
4172
  isHardBillingMessage,
4017
4173
  isUsageLimitError,
4018
4174
  localWireModelId,
@@ -4025,9 +4181,13 @@ function registerPalsuProvider(config) {
4025
4181
  redactText,
4026
4182
  redactValue,
4027
4183
  registerPalsuProvider,
4184
+ sanitizeMessagesForWire,
4028
4185
  setProviderDiagnostic,
4186
+ sliceHead,
4187
+ sliceTail,
4029
4188
  stream,
4030
4189
  toAnthropicMessages,
4031
- toOpenAIMessages
4190
+ toOpenAIMessages,
4191
+ toWellFormedText
4032
4192
  });
4033
4193
  //# sourceMappingURL=index.cjs.map