reasonix 0.5.2 → 0.5.3
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/cli/index.js +49 -22
- package/dist/cli/index.js.map +1 -1
- package/dist/index.d.ts +10 -4
- package/dist/index.js +39 -16
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -903,17 +903,23 @@ declare class CacheFirstLoop {
|
|
|
903
903
|
constructor(opts: CacheFirstLoopOptions);
|
|
904
904
|
/**
|
|
905
905
|
* Shrink the log by re-truncating oversized tool results to a tighter
|
|
906
|
-
* cap, and persist the result back to disk so the next launch
|
|
907
|
-
* re-inherit a fat session file. Returns a summary the TUI
|
|
908
|
-
* display.
|
|
906
|
+
* token cap, and persist the result back to disk so the next launch
|
|
907
|
+
* doesn't re-inherit a fat session file. Returns a summary the TUI
|
|
908
|
+
* can display.
|
|
909
|
+
*
|
|
910
|
+
* The cap is in DeepSeek V3 tokens (not chars) — so CJK text gets
|
|
911
|
+
* capped at the same effective context footprint as English instead
|
|
912
|
+
* of slipping past a char cap at 2× the token cost. Default 4000
|
|
913
|
+
* tokens, matching the token-aware dispatch cap from 0.5.2.
|
|
909
914
|
*
|
|
910
915
|
* Only tool-role messages are touched (same rationale as
|
|
911
916
|
* {@link healLoadedMessages}). User and assistant messages carry
|
|
912
917
|
* authored intent we can't mechanically shrink without losing
|
|
913
918
|
* meaning.
|
|
914
919
|
*/
|
|
915
|
-
compact(
|
|
920
|
+
compact(maxTokens?: number): {
|
|
916
921
|
healedCount: number;
|
|
922
|
+
tokensSaved: number;
|
|
917
923
|
charsSaved: number;
|
|
918
924
|
};
|
|
919
925
|
private appendAndPersist;
|
package/dist/index.js
CHANGED
|
@@ -1737,20 +1737,26 @@ var CacheFirstLoop = class {
|
|
|
1737
1737
|
}
|
|
1738
1738
|
/**
|
|
1739
1739
|
* Shrink the log by re-truncating oversized tool results to a tighter
|
|
1740
|
-
* cap, and persist the result back to disk so the next launch
|
|
1741
|
-
* re-inherit a fat session file. Returns a summary the TUI
|
|
1742
|
-
* display.
|
|
1740
|
+
* token cap, and persist the result back to disk so the next launch
|
|
1741
|
+
* doesn't re-inherit a fat session file. Returns a summary the TUI
|
|
1742
|
+
* can display.
|
|
1743
|
+
*
|
|
1744
|
+
* The cap is in DeepSeek V3 tokens (not chars) — so CJK text gets
|
|
1745
|
+
* capped at the same effective context footprint as English instead
|
|
1746
|
+
* of slipping past a char cap at 2× the token cost. Default 4000
|
|
1747
|
+
* tokens, matching the token-aware dispatch cap from 0.5.2.
|
|
1743
1748
|
*
|
|
1744
1749
|
* Only tool-role messages are touched (same rationale as
|
|
1745
1750
|
* {@link healLoadedMessages}). User and assistant messages carry
|
|
1746
1751
|
* authored intent we can't mechanically shrink without losing
|
|
1747
1752
|
* meaning.
|
|
1748
1753
|
*/
|
|
1749
|
-
compact(
|
|
1754
|
+
compact(maxTokens = 4e3) {
|
|
1750
1755
|
const before = this.log.toMessages();
|
|
1751
|
-
const { messages, healedCount,
|
|
1752
|
-
|
|
1753
|
-
|
|
1756
|
+
const { messages, healedCount, tokensSaved, charsSaved } = shrinkOversizedToolResultsByTokens(
|
|
1757
|
+
before,
|
|
1758
|
+
maxTokens
|
|
1759
|
+
);
|
|
1754
1760
|
if (healedCount > 0) {
|
|
1755
1761
|
this.log.compactInPlace(messages);
|
|
1756
1762
|
if (this.sessionName) {
|
|
@@ -1760,7 +1766,7 @@ var CacheFirstLoop = class {
|
|
|
1760
1766
|
}
|
|
1761
1767
|
}
|
|
1762
1768
|
}
|
|
1763
|
-
return { healedCount, charsSaved };
|
|
1769
|
+
return { healedCount, tokensSaved, charsSaved };
|
|
1764
1770
|
}
|
|
1765
1771
|
appendAndPersist(message) {
|
|
1766
1772
|
this.log.append(message);
|
|
@@ -2124,30 +2130,28 @@ var CacheFirstLoop = class {
|
|
|
2124
2130
|
const ratio = usage.promptTokens / ctxMax;
|
|
2125
2131
|
if (ratio > 0.6 && ratio <= 0.8) {
|
|
2126
2132
|
const before = usage.promptTokens;
|
|
2127
|
-
const soft = this.compact(
|
|
2133
|
+
const soft = this.compact(4e3);
|
|
2128
2134
|
if (soft.healedCount > 0) {
|
|
2129
|
-
const
|
|
2130
|
-
const after = Math.max(0, before - approxSaved);
|
|
2135
|
+
const after = Math.max(0, before - soft.tokensSaved);
|
|
2131
2136
|
yield {
|
|
2132
2137
|
turn: this._turn,
|
|
2133
2138
|
role: "warning",
|
|
2134
2139
|
content: `context ${before.toLocaleString()}/${ctxMax.toLocaleString()} (${Math.round(
|
|
2135
2140
|
ratio * 100
|
|
2136
|
-
)}%) \u2014 proactively compacted ${soft.healedCount} tool result(s) to
|
|
2141
|
+
)}%) \u2014 proactively compacted ${soft.healedCount} tool result(s) to 4k tokens, saved ${soft.tokensSaved.toLocaleString()} tokens (now ~${after.toLocaleString()}). Staying ahead of the 80% guard.`
|
|
2137
2142
|
};
|
|
2138
2143
|
}
|
|
2139
2144
|
}
|
|
2140
2145
|
}
|
|
2141
2146
|
if (usage && usage.promptTokens / ctxMax > 0.8) {
|
|
2142
2147
|
const before = usage.promptTokens;
|
|
2143
|
-
const compactResult = this.compact(
|
|
2148
|
+
const compactResult = this.compact(1e3);
|
|
2144
2149
|
if (compactResult.healedCount > 0) {
|
|
2145
|
-
const
|
|
2146
|
-
const after = before - approxSaved;
|
|
2150
|
+
const after = Math.max(0, before - compactResult.tokensSaved);
|
|
2147
2151
|
yield {
|
|
2148
2152
|
turn: this._turn,
|
|
2149
2153
|
role: "warning",
|
|
2150
|
-
content: `context ${before.toLocaleString()}/${ctxMax.toLocaleString()} \u2014 auto-compacted ${compactResult.healedCount} oversized tool result(s), saved
|
|
2154
|
+
content: `context ${before.toLocaleString()}/${ctxMax.toLocaleString()} \u2014 auto-compacted ${compactResult.healedCount} oversized tool result(s), saved ${compactResult.tokensSaved.toLocaleString()} tokens (now ~${after.toLocaleString()}). Continuing.`
|
|
2151
2155
|
};
|
|
2152
2156
|
} else {
|
|
2153
2157
|
yield {
|
|
@@ -2348,6 +2352,25 @@ function shrinkOversizedToolResults(messages, maxChars) {
|
|
|
2348
2352
|
});
|
|
2349
2353
|
return { messages: out, healedCount, healedFrom };
|
|
2350
2354
|
}
|
|
2355
|
+
function shrinkOversizedToolResultsByTokens(messages, maxTokens) {
|
|
2356
|
+
let healedCount = 0;
|
|
2357
|
+
let tokensSaved = 0;
|
|
2358
|
+
let charsSaved = 0;
|
|
2359
|
+
const out = messages.map((msg) => {
|
|
2360
|
+
if (msg.role !== "tool") return msg;
|
|
2361
|
+
const content = typeof msg.content === "string" ? msg.content : "";
|
|
2362
|
+
if (content.length <= maxTokens) return msg;
|
|
2363
|
+
const beforeTokens = countTokens(content);
|
|
2364
|
+
if (beforeTokens <= maxTokens) return msg;
|
|
2365
|
+
const truncated = truncateForModelByTokens(content, maxTokens);
|
|
2366
|
+
const afterTokens = countTokens(truncated);
|
|
2367
|
+
healedCount += 1;
|
|
2368
|
+
tokensSaved += Math.max(0, beforeTokens - afterTokens);
|
|
2369
|
+
charsSaved += Math.max(0, content.length - truncated.length);
|
|
2370
|
+
return { ...msg, content: truncated };
|
|
2371
|
+
});
|
|
2372
|
+
return { messages: out, healedCount, tokensSaved, charsSaved };
|
|
2373
|
+
}
|
|
2351
2374
|
function healLoadedMessages(messages, maxChars) {
|
|
2352
2375
|
const shrunk = shrinkOversizedToolResults(messages, maxChars);
|
|
2353
2376
|
let healedCount = shrunk.healedCount;
|