fix(web,cli): carry duration and byte abbreviations into the next unit (#112)
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -134,8 +134,10 @@ function humanizeDuration(ms: number): string {
|
||||
if (ms < 1000) return `${Math.round(ms)}ms`;
|
||||
const s = ms / 1000;
|
||||
if (s < 60) return `${trimZero(s)}s`;
|
||||
const m = Math.floor(s / 60);
|
||||
return `${m}m${Math.round(s % 60)}s`;
|
||||
// The minute form rounds the total before splitting it: rounding the remainder while
|
||||
// flooring the minutes lets 119.7s print as `1m60s` instead of `2m0s`.
|
||||
const whole = Math.round(s);
|
||||
return `${Math.floor(whole / 60)}m${whole % 60}s`;
|
||||
}
|
||||
|
||||
export function formatAbort(p: AbortPayload, t: Messages): string {
|
||||
|
||||
@@ -396,6 +396,23 @@ describe("StreamRenderer", () => {
|
||||
expect(last).toBe("[stats] context 7k (+3k) · tokens 11k (+7k) · 5s (+3s)");
|
||||
});
|
||||
|
||||
it("an elapsed remainder that rounds to 60s carries into the minute", () => {
|
||||
const { stream, text } = collector();
|
||||
const r = new StreamRenderer(stream, t);
|
||||
r.handle(
|
||||
tokenUsage(
|
||||
{ cache_read: 0, cache_write: 0, output: 0, total: 4000 },
|
||||
{ cache_read: 0, cache_write: 0, output: 0, total: 4000 },
|
||||
),
|
||||
);
|
||||
// 119.7s: rounding the remainder against floored minutes would read 1m60s.
|
||||
r.endTask(119_700);
|
||||
const lines = stripAnsi(text()).trim().split("\n");
|
||||
expect(lines[lines.length - 1]).toBe(
|
||||
"[stats] context 4k (+4k) · tokens 4k (+4k) · 2m0s (+2m0s)",
|
||||
);
|
||||
});
|
||||
|
||||
it("context delta goes negative after compaction shrinks the context (no clamping)", () => {
|
||||
const { stream, text } = collector();
|
||||
const r = new StreamRenderer(stream, t);
|
||||
|
||||
Reference in New Issue
Block a user