sparkecoder 0.1.139 → 0.1.140

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 (110) hide show
  1. package/dist/agent/index.d.ts +3 -3
  2. package/dist/agent/index.js +107 -6
  3. package/dist/agent/index.js.map +1 -1
  4. package/dist/cli.js +114 -6
  5. package/dist/cli.js.map +1 -1
  6. package/dist/db/index.d.ts +2 -2
  7. package/dist/{index-BAsQWqZj.d.ts → index-Cl_eUatM.d.ts} +96 -96
  8. package/dist/index.d.ts +5 -5
  9. package/dist/index.js +114 -6
  10. package/dist/index.js.map +1 -1
  11. package/dist/{schema-Dz-wABVY.d.ts → schema-BSz4MzhJ.d.ts} +3 -3
  12. package/dist/{search-CVVfuBPZ.d.ts → search-DOzC4ojH.d.ts} +4 -4
  13. package/dist/server/index.js +114 -6
  14. package/dist/server/index.js.map +1 -1
  15. package/dist/tools/index.d.ts +3 -3
  16. package/package.json +1 -1
  17. package/web/.next/BUILD_ID +1 -1
  18. package/web/.next/standalone/web/.next/BUILD_ID +1 -1
  19. package/web/.next/standalone/web/.next/build-manifest.json +2 -2
  20. package/web/.next/standalone/web/.next/prerender-manifest.json +3 -3
  21. package/web/.next/standalone/web/.next/server/app/_global-error.html +2 -2
  22. package/web/.next/standalone/web/.next/server/app/_global-error.rsc +1 -1
  23. package/web/.next/standalone/web/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  24. package/web/.next/standalone/web/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  25. package/web/.next/standalone/web/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  26. package/web/.next/standalone/web/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  27. package/web/.next/standalone/web/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  28. package/web/.next/standalone/web/.next/server/app/_not-found.html +1 -1
  29. package/web/.next/standalone/web/.next/server/app/_not-found.rsc +1 -1
  30. package/web/.next/standalone/web/.next/server/app/_not-found.segments/_full.segment.rsc +1 -1
  31. package/web/.next/standalone/web/.next/server/app/_not-found.segments/_head.segment.rsc +1 -1
  32. package/web/.next/standalone/web/.next/server/app/_not-found.segments/_index.segment.rsc +1 -1
  33. package/web/.next/standalone/web/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
  34. package/web/.next/standalone/web/.next/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
  35. package/web/.next/standalone/web/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
  36. package/web/.next/standalone/web/.next/server/app/agents.html +1 -1
  37. package/web/.next/standalone/web/.next/server/app/agents.rsc +1 -1
  38. package/web/.next/standalone/web/.next/server/app/agents.segments/!KG1haW4p/agents/__PAGE__.segment.rsc +1 -1
  39. package/web/.next/standalone/web/.next/server/app/agents.segments/!KG1haW4p/agents.segment.rsc +1 -1
  40. package/web/.next/standalone/web/.next/server/app/agents.segments/!KG1haW4p.segment.rsc +1 -1
  41. package/web/.next/standalone/web/.next/server/app/agents.segments/_full.segment.rsc +1 -1
  42. package/web/.next/standalone/web/.next/server/app/agents.segments/_head.segment.rsc +1 -1
  43. package/web/.next/standalone/web/.next/server/app/agents.segments/_index.segment.rsc +1 -1
  44. package/web/.next/standalone/web/.next/server/app/agents.segments/_tree.segment.rsc +1 -1
  45. package/web/.next/standalone/web/.next/server/app/docs/installation.html +2 -2
  46. package/web/.next/standalone/web/.next/server/app/docs/installation.rsc +1 -1
  47. package/web/.next/standalone/web/.next/server/app/docs/installation.segments/_full.segment.rsc +1 -1
  48. package/web/.next/standalone/web/.next/server/app/docs/installation.segments/_head.segment.rsc +1 -1
  49. package/web/.next/standalone/web/.next/server/app/docs/installation.segments/_index.segment.rsc +1 -1
  50. package/web/.next/standalone/web/.next/server/app/docs/installation.segments/_tree.segment.rsc +1 -1
  51. package/web/.next/standalone/web/.next/server/app/docs/installation.segments/docs/installation/__PAGE__.segment.rsc +1 -1
  52. package/web/.next/standalone/web/.next/server/app/docs/installation.segments/docs/installation.segment.rsc +1 -1
  53. package/web/.next/standalone/web/.next/server/app/docs/installation.segments/docs.segment.rsc +1 -1
  54. package/web/.next/standalone/web/.next/server/app/docs/skills.html +2 -2
  55. package/web/.next/standalone/web/.next/server/app/docs/skills.rsc +1 -1
  56. package/web/.next/standalone/web/.next/server/app/docs/skills.segments/_full.segment.rsc +1 -1
  57. package/web/.next/standalone/web/.next/server/app/docs/skills.segments/_head.segment.rsc +1 -1
  58. package/web/.next/standalone/web/.next/server/app/docs/skills.segments/_index.segment.rsc +1 -1
  59. package/web/.next/standalone/web/.next/server/app/docs/skills.segments/_tree.segment.rsc +1 -1
  60. package/web/.next/standalone/web/.next/server/app/docs/skills.segments/docs/skills/__PAGE__.segment.rsc +1 -1
  61. package/web/.next/standalone/web/.next/server/app/docs/skills.segments/docs/skills.segment.rsc +1 -1
  62. package/web/.next/standalone/web/.next/server/app/docs/skills.segments/docs.segment.rsc +1 -1
  63. package/web/.next/standalone/web/.next/server/app/docs/tools.html +2 -2
  64. package/web/.next/standalone/web/.next/server/app/docs/tools.rsc +1 -1
  65. package/web/.next/standalone/web/.next/server/app/docs/tools.segments/_full.segment.rsc +1 -1
  66. package/web/.next/standalone/web/.next/server/app/docs/tools.segments/_head.segment.rsc +1 -1
  67. package/web/.next/standalone/web/.next/server/app/docs/tools.segments/_index.segment.rsc +1 -1
  68. package/web/.next/standalone/web/.next/server/app/docs/tools.segments/_tree.segment.rsc +1 -1
  69. package/web/.next/standalone/web/.next/server/app/docs/tools.segments/docs/tools/__PAGE__.segment.rsc +1 -1
  70. package/web/.next/standalone/web/.next/server/app/docs/tools.segments/docs/tools.segment.rsc +1 -1
  71. package/web/.next/standalone/web/.next/server/app/docs/tools.segments/docs.segment.rsc +1 -1
  72. package/web/.next/standalone/web/.next/server/app/docs.html +2 -2
  73. package/web/.next/standalone/web/.next/server/app/docs.rsc +1 -1
  74. package/web/.next/standalone/web/.next/server/app/docs.segments/_full.segment.rsc +1 -1
  75. package/web/.next/standalone/web/.next/server/app/docs.segments/_head.segment.rsc +1 -1
  76. package/web/.next/standalone/web/.next/server/app/docs.segments/_index.segment.rsc +1 -1
  77. package/web/.next/standalone/web/.next/server/app/docs.segments/_tree.segment.rsc +1 -1
  78. package/web/.next/standalone/web/.next/server/app/docs.segments/docs/__PAGE__.segment.rsc +1 -1
  79. package/web/.next/standalone/web/.next/server/app/docs.segments/docs.segment.rsc +1 -1
  80. package/web/.next/standalone/web/.next/server/app/index.html +1 -1
  81. package/web/.next/standalone/web/.next/server/app/index.rsc +1 -1
  82. package/web/.next/standalone/web/.next/server/app/index.segments/!KG1haW4p/__PAGE__.segment.rsc +1 -1
  83. package/web/.next/standalone/web/.next/server/app/index.segments/!KG1haW4p.segment.rsc +1 -1
  84. package/web/.next/standalone/web/.next/server/app/index.segments/_full.segment.rsc +1 -1
  85. package/web/.next/standalone/web/.next/server/app/index.segments/_head.segment.rsc +1 -1
  86. package/web/.next/standalone/web/.next/server/app/index.segments/_index.segment.rsc +1 -1
  87. package/web/.next/standalone/web/.next/server/app/index.segments/_tree.segment.rsc +1 -1
  88. package/web/.next/standalone/web/.next/server/app/settings.html +1 -1
  89. package/web/.next/standalone/web/.next/server/app/settings.rsc +1 -1
  90. package/web/.next/standalone/web/.next/server/app/settings.segments/!KG1haW4p/settings/__PAGE__.segment.rsc +1 -1
  91. package/web/.next/standalone/web/.next/server/app/settings.segments/!KG1haW4p/settings.segment.rsc +1 -1
  92. package/web/.next/standalone/web/.next/server/app/settings.segments/!KG1haW4p.segment.rsc +1 -1
  93. package/web/.next/standalone/web/.next/server/app/settings.segments/_full.segment.rsc +1 -1
  94. package/web/.next/standalone/web/.next/server/app/settings.segments/_head.segment.rsc +1 -1
  95. package/web/.next/standalone/web/.next/server/app/settings.segments/_index.segment.rsc +1 -1
  96. package/web/.next/standalone/web/.next/server/app/settings.segments/_tree.segment.rsc +1 -1
  97. package/web/.next/standalone/web/.next/server/pages/404.html +1 -1
  98. package/web/.next/standalone/web/.next/server/pages/500.html +2 -2
  99. package/web/.next/standalone/web/.next/server/server-reference-manifest.js +1 -1
  100. package/web/.next/standalone/web/.next/server/server-reference-manifest.json +1 -1
  101. package/web/.next/standalone/web/runtime-config.json +2 -2
  102. /package/web/.next/standalone/web/.next/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_buildManifest.js +0 -0
  103. /package/web/.next/standalone/web/.next/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_clientMiddlewareManifest.json +0 -0
  104. /package/web/.next/standalone/web/.next/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_ssgManifest.js +0 -0
  105. /package/web/.next/standalone/web/.next/static/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_buildManifest.js +0 -0
  106. /package/web/.next/standalone/web/.next/static/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_clientMiddlewareManifest.json +0 -0
  107. /package/web/.next/standalone/web/.next/static/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_ssgManifest.js +0 -0
  108. /package/web/.next/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_buildManifest.js +0 -0
  109. /package/web/.next/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_clientMiddlewareManifest.json +0 -0
  110. /package/web/.next/static/{rY6TfiRfMLnxUYYyNit1Q → QkKMkVPV-LLRD2i9PBP_Y}/_ssgManifest.js +0 -0
@@ -1,6 +1,6 @@
1
1
  import 'ai';
2
- import '../schema-Dz-wABVY.js';
3
- export { A as Agent, a as AgentOptions, b as AgentRunOptions, c as AgentStreamResult, C as ContextManager, M as MessageAttachment, d as buildSystemPrompt, e as buildTaskPromptAddendum } from '../index-BAsQWqZj.js';
4
- import '../search-CVVfuBPZ.js';
2
+ import '../schema-BSz4MzhJ.js';
3
+ export { A as Agent, a as AgentOptions, b as AgentRunOptions, c as AgentStreamResult, C as ContextManager, M as MessageAttachment, d as buildSystemPrompt, e as buildTaskPromptAddendum } from '../index-Cl_eUatM.js';
4
+ import '../search-DOzC4ojH.js';
5
5
  import 'drizzle-orm/sqlite-core';
6
6
  import 'zod';
@@ -7734,6 +7734,99 @@ function capImageCount(messages, max = MAX_IMAGES_IN_CONTEXT) {
7734
7734
  return mutated ? out : messages;
7735
7735
  }
7736
7736
 
7737
+ // src/utils/sanitize-images.ts
7738
+ var SUPPORTED_IMAGE_TYPES = ["image/jpeg", "image/png", "image/gif", "image/webp"];
7739
+ var INVALID_IMAGE_PLACEHOLDER = "[invalid image omitted \u2014 the data was not a valid jpeg/png/gif/webp]";
7740
+ function hasImageMagic(bytes) {
7741
+ if (bytes.length < 12) return false;
7742
+ if (bytes[0] === 137 && bytes[1] === 80 && bytes[2] === 78 && bytes[3] === 71) return true;
7743
+ if (bytes[0] === 255 && bytes[1] === 216 && bytes[2] === 255) return true;
7744
+ if (bytes[0] === 71 && bytes[1] === 73 && bytes[2] === 70 && bytes[3] === 56) return true;
7745
+ if (bytes[0] === 82 && bytes[1] === 73 && bytes[2] === 70 && bytes[3] === 70 && bytes[8] === 87 && bytes[9] === 69 && bytes[10] === 66 && bytes[11] === 80) return true;
7746
+ return false;
7747
+ }
7748
+ function extractBase64(part) {
7749
+ const raw = typeof part?.data === "string" ? part.data : typeof part?.image === "string" ? part.image : null;
7750
+ if (typeof raw !== "string" || raw.length === 0) return null;
7751
+ if (/^https?:\/\//i.test(raw)) return null;
7752
+ const dataUrl = raw.match(/^data:[^;,]+;base64,([\s\S]*)$/);
7753
+ return dataUrl ? dataUrl[1] : raw;
7754
+ }
7755
+ function isInvalidImagePart(part) {
7756
+ if (!part || typeof part !== "object") return false;
7757
+ const t = part.type;
7758
+ if (t !== "image" && t !== "image-data" && t !== "media") return false;
7759
+ const mt = part.mediaType;
7760
+ const b64 = extractBase64(part);
7761
+ if (b64 === null) {
7762
+ return typeof mt === "string" && mt.startsWith("image/") && !SUPPORTED_IMAGE_TYPES.includes(mt);
7763
+ }
7764
+ let bytes;
7765
+ try {
7766
+ bytes = Buffer.from(b64, "base64");
7767
+ } catch {
7768
+ return true;
7769
+ }
7770
+ if (bytes.length === 0) return true;
7771
+ return !hasImageMagic(bytes);
7772
+ }
7773
+ function placeholder() {
7774
+ return { type: "text", text: INVALID_IMAGE_PLACEHOLDER };
7775
+ }
7776
+ function sanitizeInvalidImages(messages) {
7777
+ if (!Array.isArray(messages) || messages.length === 0) return messages;
7778
+ let mutated = false;
7779
+ let dropped = 0;
7780
+ const out = messages.slice();
7781
+ for (let i = 0; i < out.length; i++) {
7782
+ const msg = out[i];
7783
+ if (!Array.isArray(msg.content)) continue;
7784
+ let contentCloned = false;
7785
+ const ensureCloned = () => {
7786
+ if (contentCloned) return;
7787
+ out[i] = { ...msg, content: [...msg.content] };
7788
+ contentCloned = true;
7789
+ };
7790
+ const content = () => out[i].content;
7791
+ for (let j = 0; j < content().length; j++) {
7792
+ const part = content()[j];
7793
+ if (isInvalidImagePart(part)) {
7794
+ ensureCloned();
7795
+ out[i].content[j] = placeholder();
7796
+ mutated = true;
7797
+ dropped++;
7798
+ continue;
7799
+ }
7800
+ if (part && typeof part === "object" && part.type === "tool-result" && part.output && part.output.type === "content" && Array.isArray(part.output.value)) {
7801
+ const innerValue = part.output.value;
7802
+ let innerMutated = false;
7803
+ const newValue = innerValue.slice();
7804
+ for (let k = 0; k < newValue.length; k++) {
7805
+ if (isInvalidImagePart(newValue[k])) {
7806
+ newValue[k] = placeholder();
7807
+ innerMutated = true;
7808
+ dropped++;
7809
+ }
7810
+ }
7811
+ if (innerMutated) {
7812
+ ensureCloned();
7813
+ out[i].content[j] = {
7814
+ ...part,
7815
+ output: { ...part.output, value: newValue }
7816
+ };
7817
+ mutated = true;
7818
+ }
7819
+ }
7820
+ }
7821
+ }
7822
+ if (mutated) {
7823
+ console.warn(
7824
+ `[sanitize-images] Replaced ${dropped} invalid image part(s) with a text placeholder (non-image bytes / unsupported type) to avoid provider 400 "invalid image" errors.`
7825
+ );
7826
+ }
7827
+ return mutated ? out : messages;
7828
+ }
7829
+
7737
7830
  // src/agent/model-limits.ts
7738
7831
  var MODEL_LIMITS = {
7739
7832
  "claude-opus-4-8": { contextWindow: 2e5, rollingTarget: 15e4 },
@@ -7813,6 +7906,7 @@ ${summaryContent}`
7813
7906
  messages = repairToolPairing(messages);
7814
7907
  messages = ensureToolResultsFollowCalls(messages);
7815
7908
  messages = ensureEndsWithUserOrTool(messages);
7909
+ messages = sanitizeInvalidImages(messages);
7816
7910
  messages = capImageCount(messages);
7817
7911
  messages = this.enforceHardCap(messages);
7818
7912
  return messages;
@@ -7824,28 +7918,35 @@ ${summaryContent}`
7824
7918
  * repairs tool pairing so dropping can't orphan a tool result.
7825
7919
  */
7826
7920
  enforceHardCap(messages) {
7827
- const { contextWindow } = getModelLimits(this.modelId);
7828
- const ceiling = Math.max(2e4, Math.floor(contextWindow * 0.9));
7921
+ const { rollingTarget } = getModelLimits(this.modelId);
7922
+ const MAX_MESSAGES = 120;
7923
+ const tokenCeiling = Math.max(2e4, Math.floor(rollingTarget * 1.5));
7829
7924
  const tokens = messages.map((m) => this.messageTokens(m));
7830
7925
  let total = tokens.reduce((a, b) => a + b, 0);
7831
- if (total <= ceiling) return messages;
7832
7926
  const hasLeadingSummary = messages.length > 0 && messages[0].role === "system";
7833
7927
  const firstBody = hasLeadingSummary ? 1 : 0;
7834
7928
  const lastIndex = messages.length - 1;
7929
+ const bodyCount = messages.length - firstBody;
7930
+ if (bodyCount <= MAX_MESSAGES && total <= tokenCeiling) return messages;
7835
7931
  let start = firstBody;
7836
- while (start < lastIndex && total > ceiling) {
7932
+ const countDropTarget = messages.length - MAX_MESSAGES;
7933
+ while (start < countDropTarget && start < lastIndex) {
7934
+ total -= tokens[start];
7935
+ start += 1;
7936
+ }
7937
+ while (start < lastIndex && total > tokenCeiling) {
7837
7938
  total -= tokens[start];
7838
7939
  start += 1;
7839
7940
  }
7840
7941
  let out = hasLeadingSummary ? [messages[0], ...messages.slice(start)] : messages.slice(start);
7841
- if (total > ceiling) {
7942
+ if (total > tokenCeiling) {
7842
7943
  out = out.map((m) => hardTruncateMessageText(m));
7843
7944
  }
7844
7945
  out = repairToolPairing(out);
7845
7946
  out = ensureToolResultsFollowCalls(out);
7846
7947
  out = ensureEndsWithUserOrTool(out);
7847
7948
  console.warn(
7848
- `[Context] hard cap engaged for ${this.modelId}: trimmed ${messages.length}\u2192${out.length} msgs (ceiling ${ceiling} tokens).`
7949
+ `[Context] hard cap engaged for ${this.modelId}: trimmed ${messages.length}\u2192${out.length} msgs (ceiling ${tokenCeiling} est-tokens / ${MAX_MESSAGES} msgs).`
7849
7950
  );
7850
7951
  return out;
7851
7952
  }