fix(agent-usage): centralize DisplayTotal, re-sort by display tier, split caveat

Fold Thufir's three blocking amendments into cbfbe1ed0:

1. Centralize display metric as DisplayTotal {kind, value, partial}.
   deriveApproxTotal() replaced by deriveDisplayTotal() returning an
   explicit exact|approximate|unknown discriminant with provenance:
   - exact: totalTokens.value present; partial mirrors wire incomplete flag
   - approximate: totalTokens null, i/o known; value = bigint-safe i/o sum;
     partial = inputTokens.incomplete || outputTokens.incomplete
   - unknown: no token counts at all; value null, partial false
   All surfaces (Section header/bars/rows, DailyBars, FocusedView stat)
   now consume this single result — no surface can drift independently.

2. Re-sort agents/models by display tier.
   sortAgentsByKnownTotal/sortModelsByKnownTotal replaced by
   sortAgentsByDisplayTotal/sortModelsByDisplayTotal using a three-tier
   key (exact=0, approximate=1, unknown=2), descending by value within
   tier, then existing tiebreaks. With all-null prod totals the list
   order and bar widths now agree instead of disagreeing.

3. Split caveat paragraph into per-condition sentences.
   The single agent-usage-focused-partial-explanation block replaced by
   two separately-gated <p> elements:
   - agent-usage-focused-unknown-intervals-caveat: gates on hasUnknownUsage
   - agent-usage-focused-invalid-reports-caveat: gates on invalidReportCount > 0
   Each sentence claims only what its gate proves.

Test updates:
- deriveApproxTotal tests replaced with deriveDisplayTotal tests covering
  all three kinds, partial provenance, and i/o-only combinations.
- Sort tests updated for new export names and assertions.
- Mixed exact/approximate/unknown population tests added for both
  sortAgentsByDisplayTotal and sortModelsByDisplayTotal.
- e2e spec updated from single partial-explanation testid to the two
  per-condition testids.
- 3567 tests pass, tsc --noEmit clean.

Co-authored-by: Will Pfleger <pfleger.will@gmail.com>
Signed-off-by: Will Pfleger <pfleger.will@gmail.com>
This commit is contained in:
npub1mn7jgtj4w2pd0g0zeuhxsa6jy6p0rewxz4kujt98my82ahfmp72sxjexk7
2026-07-29 14:23:51 -04:00
co-authored by Will Pfleger
parent cbfbe1ed05
commit b384fc9a56
6 changed files with 274 additions and 173 deletions
@@ -4,7 +4,7 @@ import test from "node:test";
import {
bigintRatio,
buildLocalDayBoundaries,
deriveApproxTotal,
deriveDisplayTotal,
deriveUsageIngressTrailing,
formatCoverageDate,
formatEstimatedCostUsd,
@@ -14,8 +14,8 @@ import {
isUnknownField,
msUntilNextLocalMidnight,
parseTokenCount,
sortAgentsByKnownTotal,
sortModelsByKnownTotal,
sortAgentsByDisplayTotal,
sortModelsByDisplayTotal,
sumKnownBucketTotals,
} from "./agentUsage.ts";
@@ -334,122 +334,214 @@ test("bigintRatio clamps part to [0, whole]", () => {
assert.equal(bigintRatio(200n, 100n), 1);
});
// ── deriveApproxTotal ─────────────────────────────────────────────────────────
// ── deriveDisplayTotal ────────────────────────────────────────────────────────
test("deriveApproxTotal returns null when genuine total is known (no approximation needed)", () => {
test("deriveDisplayTotal returns exact kind when totalTokens is present", () => {
const usage = reportedUsage({
inputTokens: usageField({ value: "800" }),
outputTokens: usageField({ value: "200" }),
totalTokens: usageField({ value: "1100" }),
});
assert.equal(deriveApproxTotal(usage), null);
const dt = deriveDisplayTotal(usage);
assert.equal(dt.kind, "exact");
assert.equal(dt.value, 1100n);
assert.equal(dt.partial, false);
});
test("deriveApproxTotal sums input and output when total is null", () => {
test("deriveDisplayTotal carries partial=true for an exact total flagged incomplete", () => {
const usage = reportedUsage({
totalTokens: usageField({ value: "900", incomplete: true }),
});
const dt = deriveDisplayTotal(usage);
assert.equal(dt.kind, "exact");
assert.equal(dt.value, 900n);
assert.equal(dt.partial, true);
});
test("deriveDisplayTotal returns approximate kind when totalTokens is null but i/o is known", () => {
const usage = reportedUsage({
inputTokens: usageField({ value: "800" }),
outputTokens: usageField({ value: "200" }),
});
assert.equal(deriveApproxTotal(usage), 1000n);
const dt = deriveDisplayTotal(usage);
assert.equal(dt.kind, "approximate");
assert.equal(dt.value, 1000n);
assert.equal(dt.partial, false);
});
test("deriveApproxTotal returns input alone when output is null", () => {
test("deriveDisplayTotal approximate partial=true when either i/o field is incomplete", () => {
const usage = reportedUsage({
inputTokens: usageField({ value: "800", incomplete: true }),
outputTokens: usageField({ value: "200" }),
});
const dt = deriveDisplayTotal(usage);
assert.equal(dt.kind, "approximate");
assert.equal(dt.partial, true);
});
test("deriveDisplayTotal returns approximate from input alone when output is null", () => {
const usage = reportedUsage({
inputTokens: usageField({ value: "500" }),
});
assert.equal(deriveApproxTotal(usage), 500n);
const dt = deriveDisplayTotal(usage);
assert.equal(dt.kind, "approximate");
assert.equal(dt.value, 500n);
});
test("deriveApproxTotal returns output alone when input is null", () => {
test("deriveDisplayTotal returns approximate from output alone when input is null", () => {
const usage = reportedUsage({
outputTokens: usageField({ value: "300" }),
});
assert.equal(deriveApproxTotal(usage), 300n);
const dt = deriveDisplayTotal(usage);
assert.equal(dt.kind, "approximate");
assert.equal(dt.value, 300n);
});
test("deriveApproxTotal returns null when total, input, and output are all null", () => {
test("deriveDisplayTotal returns unknown kind when all fields are null", () => {
const usage = reportedUsage();
assert.equal(deriveApproxTotal(usage), null);
const dt = deriveDisplayTotal(usage);
assert.equal(dt.kind, "unknown");
assert.equal(dt.value, null);
assert.equal(dt.partial, false);
});
// ── sortAgentsByKnownTotal / sortModelsByKnownTotal ─────────────────────────
// ── sortAgentsByDisplayTotal / sortModelsByDisplayTotal ─────────────────────
test("sortAgentsByKnownTotal ranks known totals descending", () => {
test("sortAgentsByDisplayTotal ranks known exact totals descending", () => {
const agents = [
agentUsage("a1", "100"),
agentUsage("a2", "300"),
agentUsage("a3", "200"),
];
const sorted = sortAgentsByKnownTotal(agents);
const sorted = sortAgentsByDisplayTotal(agents);
assert.deepEqual(
sorted.map((a) => a.agentPubkey),
["a2", "a3", "a1"],
);
});
test("sortAgentsByKnownTotal lists unknown-total agents after all known-total agents, never interleaved", () => {
test("sortAgentsByDisplayTotal ranks exact totals above approximate totals", () => {
const exactAgent = agentUsage("exact", "50");
const approxAgent = agentUsage("approx", null, {
usage: reportedUsage({
inputTokens: usageField({ value: "9000" }),
outputTokens: usageField({ value: "9000" }),
}),
});
const sorted = sortAgentsByDisplayTotal([approxAgent, exactAgent]);
// exact(50) < approximate(18000) numerically, but exact tier wins
assert.equal(sorted[0].agentPubkey, "exact");
assert.equal(sorted[1].agentPubkey, "approx");
});
test("sortAgentsByDisplayTotal ranks approximate totals above unknown totals", () => {
const approxAgent = agentUsage("approx", null, {
usage: reportedUsage({
inputTokens: usageField({ value: "100" }),
}),
});
const unknownAgent = agentUsage("unknown", null);
const sorted = sortAgentsByDisplayTotal([unknownAgent, approxAgent]);
assert.equal(sorted[0].agentPubkey, "approx");
assert.equal(sorted[1].agentPubkey, "unknown");
});
test("sortAgentsByDisplayTotal handles mixed exact/approximate/unknown population in tier order", () => {
const agents = [
agentUsage("u1", null), // unknown
agentUsage("e1", "100"), // exact
agentUsage("a1", null, { // approximate
usage: reportedUsage({ inputTokens: usageField({ value: "500" }) }),
}),
agentUsage("u2", null), // unknown
agentUsage("e2", "300"), // exact
agentUsage("a2", null, { // approximate
usage: reportedUsage({ inputTokens: usageField({ value: "200" }) }),
}),
];
const sorted = sortAgentsByDisplayTotal(agents);
// Tier order: exact first (e2=300 > e1=100), then approx (a1=500 > a2=200), then unknown (u1 < u2 by pubkey)
assert.deepEqual(
sorted.map((a) => a.agentPubkey),
["e2", "e1", "a1", "a2", "u1", "u2"],
);
});
test("sortAgentsByDisplayTotal lists unknown-total agents after all other agents, tiebroken by pubkey", () => {
const agents = [
agentUsage("unknown-b", null),
agentUsage("known", "50"),
agentUsage("unknown-a", null),
];
const sorted = sortAgentsByKnownTotal(agents);
const sorted = sortAgentsByDisplayTotal(agents);
assert.equal(sorted[0].agentPubkey, "known");
// Unknown-total agents tiebreak by normalized pubkey.
assert.deepEqual(
sorted.slice(1).map((a) => a.agentPubkey),
["unknown-a", "unknown-b"],
);
});
test("sortAgentsByKnownTotal tiebreaks equal known totals by pubkey", () => {
test("sortAgentsByDisplayTotal tiebreaks equal exact totals by pubkey", () => {
const agents = [agentUsage("b", "100"), agentUsage("a", "100")];
const sorted = sortAgentsByKnownTotal(agents);
const sorted = sortAgentsByDisplayTotal(agents);
assert.deepEqual(
sorted.map((a) => a.agentPubkey),
["a", "b"],
);
});
test("sortModelsByKnownTotal sorts null model ('Unknown model') last among ties", () => {
test("sortModelsByDisplayTotal sorts null model ('Unknown model') last among ties", () => {
const models = [
modelUsage(null, "100"),
modelUsage("gpt-4", "100"),
modelUsage("claude", "100"),
];
const sorted = sortModelsByKnownTotal(models);
const sorted = sortModelsByDisplayTotal(models);
assert.deepEqual(
sorted.map((m) => m.model),
["claude", "gpt-4", null],
);
});
test("sortModelsByKnownTotal tiebreaks harness before model when totals are equal", () => {
test("sortModelsByDisplayTotal tiebreaks harness before model when totals are equal", () => {
const models = [
modelUsage("m", "100", { harness: "z-harness" }),
modelUsage("m", "100", { harness: "a-harness" }),
modelUsage("m", "100", { harness: null }),
];
const sorted = sortModelsByKnownTotal(models);
const sorted = sortModelsByDisplayTotal(models);
assert.deepEqual(
sorted.map((m) => m.harness),
["a-harness", "z-harness", null],
);
});
test("sortModelsByKnownTotal same model two harnesses produces two rows in harness order", () => {
test("sortModelsByDisplayTotal same model two harnesses produces two rows in harness order", () => {
// Same model via two harnesses should be distinct rows; harness-ascending tiebreak.
const models = [
modelUsage("claude-sonnet", "500", { harness: "goose" }),
modelUsage("claude-sonnet", "500", { harness: "claude-code" }),
];
const sorted = sortModelsByKnownTotal(models);
const sorted = sortModelsByDisplayTotal(models);
assert.deepEqual(
sorted.map((m) => m.harness),
["claude-code", "goose"],
);
});
test("sortModelsByDisplayTotal ranks exact tier above approximate tier regardless of value", () => {
const exactModel = modelUsage("small-model", "10");
const approxModel = modelUsage("big-approx", null, {
usage: reportedUsage({
inputTokens: usageField({ value: "9999" }),
outputTokens: usageField({ value: "9999" }),
}),
});
const sorted = sortModelsByDisplayTotal([approxModel, exactModel]);
assert.equal(sorted[0].model, "small-model"); // exact tier wins
assert.equal(sorted[1].model, "big-approx");
});
// ── isPartialField / isUnknownField ──────────────────────────────────────────
test("isPartialField is true only for a known value flagged incomplete", () => {
@@ -189,85 +189,119 @@ export function bigintRatio(part: bigint, whole: bigint): number {
return Number(permille) / 1000;
}
// ── Display approximation (A2 presentation layer) ────────────────────────────
// ── Display total derivation (A2 presentation layer) ─────────────────────────
/**
* Derive a display approximation of the total by summing known input and output
* token counts. Returns `null` if neither field is known. This is a *display
* label* only — it is NEVER written to the wire or stored; NIP-AM's
* "MUST NOT derive total = input + output" governs published/stored data only.
* Callers MUST prefix the result with `≈` so the approximation is honest.
* A provenance-bearing display total for the usage UI. Only one of three
* states is ever active:
*
* - `exact`: `totalTokens.value` is present and parsed. `partial` mirrors the
* wire field's `incomplete` flag.
* - `approximate`: `totalTokens.value` is absent but at least one of
* `inputTokens` / `outputTokens` is known; `value` is their bigint-safe sum.
* `partial` is `inputTokens.incomplete || outputTokens.incomplete`.
* Callers MUST render `≈` to distinguish this from a provider total.
* - `unknown`: no token counts are available at all; `value` is `null`.
*
* This is a *display* value only — it is NEVER written to the wire or stored.
* NIP-AM's "MUST NOT derive total = input + output" governs published/stored
* data; this label lives entirely in the presentation layer.
*/
export function deriveApproxTotal(usage: {
export type DisplayTotal =
| { kind: "exact"; value: bigint; partial: boolean }
| { kind: "approximate"; value: bigint; partial: boolean }
| { kind: "unknown"; value: null; partial: false };
export function deriveDisplayTotal(usage: {
inputTokens: UsageField;
outputTokens: UsageField;
totalTokens: UsageField;
}): bigint | null {
if (parseTokenCount(usage.totalTokens.value) !== null) {
// Genuine total is known — callers should use it directly; no approximation needed.
return null;
}): DisplayTotal {
const exact = parseTokenCount(usage.totalTokens.value);
if (exact !== null) {
return { kind: "exact", value: exact, partial: isPartialField(usage.totalTokens) };
}
const input = parseTokenCount(usage.inputTokens.value);
const output = parseTokenCount(usage.outputTokens.value);
if (input === null && output === null) return null;
return (input ?? 0n) + (output ?? 0n);
if (input !== null || output !== null) {
return {
kind: "approximate",
value: (input ?? 0n) + (output ?? 0n),
partial: isPartialField(usage.inputTokens) || isPartialField(usage.outputTokens),
};
}
return { kind: "unknown", value: null, partial: false };
}
// ── Ranking (A2: known lower-bound totals rank; null totals list after) ─────
// ── Ranking (A2: rank by display total — exact > approximate > unknown) ──────
type Ranked<T> = { item: T; totalTokens: bigint | null };
type DisplayTierKey = 0 | 1 | 2; // 0 = exact, 1 = approximate, 2 = unknown
function rankByKnownTotal<T>(
type RankedWithDisplay<T> = {
item: T;
displayTotal: DisplayTotal;
tierKey: DisplayTierKey;
};
function tierOf(dt: DisplayTotal): DisplayTierKey {
if (dt.kind === "exact") return 0;
if (dt.kind === "approximate") return 1;
return 2;
}
/**
* Sort items by their display total:
* 1. Exact totals rank first, descending by value.
* 2. Approximate totals (≈ in+out) rank next, descending by value.
* 3. Unknown totals rank last, unordered beyond the tiebreak.
* Within the same tier and value, `tiebreak` resolves the order.
*/
function rankByDisplayTotal<T>(
items: readonly T[],
totalTokens: (item: T) => UsageField,
getUsage: (item: T) => { inputTokens: UsageField; outputTokens: UsageField; totalTokens: UsageField },
tiebreak: (a: T, b: T) => number,
): T[] {
const withTotals: Ranked<T>[] = items.map((item) => ({
item,
totalTokens: parseTokenCount(totalTokens(item).value),
}));
const withDisplay: RankedWithDisplay<T>[] = items.map((item) => {
const dt = deriveDisplayTotal(getUsage(item));
return { item, displayTotal: dt, tierKey: tierOf(dt) };
});
return withTotals
return withDisplay
.sort((a, b) => {
if (a.totalTokens !== null && b.totalTokens !== null) {
if (a.totalTokens !== b.totalTokens) {
return a.totalTokens > b.totalTokens ? -1 : 1;
if (a.tierKey !== b.tierKey) return a.tierKey - b.tierKey;
// Same tier — for exact/approximate, sort descending by value.
if (a.displayTotal.value !== null && b.displayTotal.value !== null) {
if (a.displayTotal.value !== b.displayTotal.value) {
return a.displayTotal.value > b.displayTotal.value ? -1 : 1;
}
return tiebreak(a.item, b.item);
}
// Known-total rows rank before unknown-total rows; never interleave.
if (a.totalTokens !== null) return -1;
if (b.totalTokens !== null) return 1;
return tiebreak(a.item, b.item);
})
.map((ranked) => ranked.item);
}
/** Agents sort by known `totalTokens` descending, then normalized pubkey (A2/plan). Unknown-total agents list after all known-total agents, unranked among themselves beyond the pubkey tiebreak. */
export function sortAgentsByKnownTotal(
/** Agents sort by display total (exact → approximate → unknown), descending by value within tier, then normalized pubkey. */
export function sortAgentsByDisplayTotal(
agents: readonly AgentUsage[],
): AgentUsage[] {
return rankByKnownTotal(
return rankByDisplayTotal(
agents,
(agent) => agent.usage.totalTokens,
(agent) => agent.usage,
(a, b) => a.agentPubkey.localeCompare(b.agentPubkey),
);
}
/** Model rows use the same ranking rule as agents, tiebroken by harness name
/** Model rows use the same display-total ranking, tiebroken by harness name
* (null harness sorts last), then by model name (null model sorts last).
* Ordinal (`<`/`>`) comparators are used so ordering is locale-independent
* and matches the Rust backend's `String::cmp` byte order.
* Note: harness/model identifiers are ASCII in practice; UTF-16 vs UTF-8
* scalar divergence for astral code points is accepted and not a use case. */
export function sortModelsByKnownTotal(
* and matches the Rust backend's `String::cmp` byte order. */
export function sortModelsByDisplayTotal(
models: readonly AgentUsageModel[],
): AgentUsageModel[] {
return rankByKnownTotal(
return rankByDisplayTotal(
models,
(model) => model.usage.totalTokens,
(model) => model.usage,
(a, b) => {
// Harness tiebreak first (ordinal, None last).
const harnessCmp =
a.harness === b.harness
? 0
@@ -279,7 +313,6 @@ export function sortModelsByKnownTotal(
? -1
: 1;
if (harnessCmp !== 0) return harnessCmp;
// Then model (ordinal, None last).
if (a.model === b.model) return 0;
if (a.model === null) return 1;
if (b.model === null) return -1;
@@ -370,9 +403,9 @@ export function sumKnownBucketTotals(
partial = true;
}
if (known === null) {
const approx = deriveApproxTotal(bucket.usage);
if (approx !== null) {
approxSum += approx;
const dt = deriveDisplayTotal(bucket.usage);
if (dt.kind === "approximate") {
approxSum += dt.value;
sawApprox = true;
}
}
@@ -4,7 +4,7 @@ import { cn } from "@/shared/lib/cn";
import type { AgentUsageSeriesBucket } from "@/shared/api/tauriArchive";
import {
bigintRatio,
deriveApproxTotal,
deriveDisplayTotal,
formatTokenCountCompact,
isPartialField,
parseTokenCount,
@@ -66,13 +66,13 @@ function deriveBarState(bucket: AgentUsageSeriesBucket) {
knownTokens: known,
};
}
// Genuine total unknown — try i/o approximation before falling back to hatched.
const approx = deriveApproxTotal(bucket.usage);
if (approx !== null) {
// Genuine total unknown — derive the display total for the bar.
const dt = deriveDisplayTotal(bucket.usage);
if (dt.kind === "approximate") {
return {
accessibleLabel: `${dateLabel} · ≈ ${formatTokenCountCompact(approx)} tokens (approx)`,
accessibleLabel: `${dateLabel} · ≈ ${formatTokenCountCompact(dt.value)} tokens (approx)`,
kind: "approx" as const,
knownTokens: approx,
knownTokens: dt.value,
};
}
return {
@@ -101,10 +101,10 @@ export function AgentUsageDailyBars({
buckets.reduce<bigint>((max, bucket) => {
const total = parseTokenCount(bucket.usage.totalTokens.value);
if (total !== null) return total > max ? total : max;
// Fall back to the i/o approximation so bars scale correctly when
// no bucket reports a genuine total.
const approx = deriveApproxTotal(bucket.usage);
return approx !== null && approx > max ? approx : max;
// Fall back to the display total's approximate value so bars scale
// correctly when no bucket reports a genuine total.
const dt = deriveDisplayTotal(bucket.usage);
return dt.kind === "approximate" && dt.value > max ? dt.value : max;
}, 0n),
[buckets],
);
@@ -14,15 +14,16 @@ import { Skeleton } from "@/shared/ui/skeleton";
import { Tabs, TabsList, TabsTrigger } from "@/shared/ui/tabs";
import { useAgentUsageSeries } from "../hooks";
import {
deriveDisplayTotal,
formatCoverageDate,
formatEstimatedCostUsd,
formatTokenCountCompact,
formatTokenCountExact,
deriveApproxTotal,
isPartialField,
isUnknownField,
parseTokenCount,
sortModelsByKnownTotal,
sortModelsByDisplayTotal,
type DisplayTotal,
type UsageWindowDays,
} from "../lib/agentUsage";
import { AgentUsageDailyBars } from "./AgentUsageDailyBars";
@@ -204,28 +205,29 @@ function AgentUsageFocusedTotals({
agent: AgentUsageSeries["agents"][number];
coverage: AgentUsageSeries["coverage"];
}) {
const { estimatedCostUsd, inputTokens, outputTokens, totalTokens } =
const { estimatedCostUsd, inputTokens, outputTokens } =
agent.usage;
const models = sortModelsByKnownTotal(agent.models);
// Show the caveat paragraph only when there are genuinely invalid/excluded
// rows or truly unknown i/o deltas. `agent.hasUnknownUsage` is true when
// deltaReliable is false (some intervals couldn't be computed). The
// `coverage.invalidReportCount > 0` path covers rows excluded from buckets.
// We do NOT trigger on totalTokens.value being null: that's the permanent
// state for all real publishers today (no harness emits a total yet), and
// showing the caveat permanently would make it read as a persistent error.
const explainPartial =
agent.hasUnknownUsage || coverage.invalidReportCount > 0;
const models = sortModelsByDisplayTotal(agent.models);
// `explainPartial` controls the caveat paragraph. Each sentence is gated
// only on the condition that proves it:
// - unknown-intervals sentence: `agent.hasUnknownUsage` — true when
// deltaReliable is false for at least one interval in the window.
// - invalid-reports sentence: `coverage.invalidReportCount > 0` — true
// when rows were excluded from buckets due to bad timestamps or missing
// session cumulative totals.
// We do NOT trigger on totalTokens.value being null — that's the permanent
// state for all real publishers today, not a data quality problem.
const showUnknownIntervalsCaveat = agent.hasUnknownUsage;
const showInvalidReportsCaveat = coverage.invalidReportCount > 0;
// Approximation for the Total tokens stat when no genuine total is available.
const approxTotal = deriveApproxTotal(agent.usage);
// Display total for the Total tokens stat.
const displayTotal = deriveDisplayTotal(agent.usage);
return (
<Card className="space-y-4 p-6" data-testid="agent-usage-focused-totals">
<div className="grid grid-cols-2 gap-4 sm:grid-cols-4">
<ApproxTokenStat
approxTotal={approxTotal}
field={totalTokens}
displayTotal={displayTotal}
label="Total tokens"
/>
<TokenStat field={inputTokens} label="Input tokens" />
@@ -300,11 +302,19 @@ function AgentUsageFocusedTotals({
{" · "}
{formatCoverageRange(coverage)}
</p>
{explainPartial ? (
<p data-testid="agent-usage-focused-partial-explanation">
Some usage could not be counted: reports with an unreadable
timestamp or a cumulative total missing its session are excluded,
and unknown intervals are omitted rather than shown as zero.
{showUnknownIntervalsCaveat ? (
<p data-testid="agent-usage-focused-unknown-intervals-caveat">
Some usage could not be counted: unknown intervals are omitted
rather than shown as zero.
</p>
) : null}
{showInvalidReportsCaveat ? (
<p data-testid="agent-usage-focused-invalid-reports-caveat">
{coverage.invalidReportCount === 1
? "1 report"
: `${coverage.invalidReportCount} reports`}{" "}
excluded: reports with an unreadable timestamp or a cumulative
total missing its session are not assigned to any day.
</p>
) : null}
</div>
@@ -335,23 +345,20 @@ function TokenStat({
* honest without hiding that real token activity was counted.
*/
function ApproxTokenStat({
approxTotal,
field,
displayTotal,
label,
}: {
approxTotal: bigint | null;
field: { value: string | null; incomplete: boolean };
displayTotal: DisplayTotal;
label: string;
}) {
const parsed = parseTokenCount(field.value);
const display =
parsed !== null
? formatTokenCountExact(parsed)
: approxTotal !== null
? `≈ ${formatTokenCountExact(approxTotal)}`
displayTotal.kind === "exact"
? formatTokenCountExact(displayTotal.value)
: displayTotal.kind === "approximate"
? `≈ ${formatTokenCountExact(displayTotal.value)}`
: null;
return (
<UsageStat display={display} isPartial={isPartialField(field)} label={label} />
<UsageStat display={display} isPartial={displayTotal.partial} label={label} />
);
}
@@ -21,13 +21,10 @@ import { Tabs, TabsList, TabsTrigger } from "@/shared/ui/tabs";
import { useAgentUsageSeries } from "../hooks";
import {
bigintRatio,
deriveApproxTotal,
deriveDisplayTotal,
formatCoverageDate,
formatTokenCountCompact,
isPartialField,
isUnknownField,
parseTokenCount,
sortAgentsByKnownTotal,
sortAgentsByDisplayTotal,
sumKnownBucketTotals,
type UsageWindowDays,
} from "../lib/agentUsage";
@@ -51,7 +48,7 @@ export function AgentUsageSection({
const { onOpenSettings } = useAppShell();
const agents = React.useMemo(
() => sortAgentsByKnownTotal(query.data?.agents ?? []),
() => sortAgentsByDisplayTotal(query.data?.agents ?? []),
[query.data?.agents],
);
const pubkeys = React.useMemo(
@@ -155,17 +152,13 @@ function AgentUsageCard({
series.coverage.invalidReportCount > 0;
// Relative bars are decorative (aria-hidden, per plan) — scale each agent's
// known total (or i/o approximation) against the largest such value in the
// current window so the sorted-by-total list also reads as a bar chart.
const maxKnownTotal = React.useMemo(
// display total (exact or approximate) against the largest such value in the
// current window so the sorted-by-display-total list also reads as a bar chart.
const maxDisplayValue = React.useMemo(
() =>
agents.reduce<bigint>((max, agent) => {
const total = parseTokenCount(agent.usage.totalTokens.value);
if (total !== null) return total > max ? total : max;
// Fall back to the i/o approximation so bars are still visible when
// no agent reports a genuine total.
const approx = deriveApproxTotal(agent.usage);
return approx !== null && approx > max ? approx : max;
const dt = deriveDisplayTotal(agent.usage);
return dt.value !== null && dt.value > max ? dt.value : max;
}, 0n),
[agents],
);
@@ -229,7 +222,7 @@ function AgentUsageCard({
days={days}
key={agent.agentPubkey}
label={resolveUserLabel({ profiles, pubkey: agent.agentPubkey })}
maxKnownTotal={maxKnownTotal}
maxDisplayValue={maxDisplayValue}
onOpenAgentProfile={onOpenAgentProfile}
profileAvatarUrl={
profiles?.[agent.agentPubkey]?.avatarUrl ?? null
@@ -257,44 +250,28 @@ function AgentUsageRow({
agent,
days,
label,
maxKnownTotal,
maxDisplayValue,
onOpenAgentProfile,
profileAvatarUrl,
}: {
agent: AgentUsage;
days: UsageWindowDays;
label: string;
maxKnownTotal: bigint;
maxDisplayValue: bigint;
onOpenAgentProfile: (
pubkey: string,
options?: ProfilePanelOpenOptions,
) => void;
profileAvatarUrl: string | null;
}) {
const total = agent.usage.totalTokens;
const knownTotal = parseTokenCount(total.value);
const partial = isPartialField(total);
const unknown = isUnknownField(total);
// When total is null (unknown), check whether any displayed I/O field is
// incomplete — per-field partial truth must be preserved at every seam (A2).
const ioPartial =
knownTotal === null &&
(isPartialField(agent.usage.inputTokens) ||
isPartialField(agent.usage.outputTokens));
// Approximate total for display when no genuine total is available.
const approxTotal =
knownTotal === null ? deriveApproxTotal(agent.usage) : null;
// Effective value for the relative bar width — prefer genuine total, then approx.
const barTotal = knownTotal ?? approxTotal;
const dt = deriveDisplayTotal(agent.usage);
const trailing =
knownTotal !== null
? formatTokenCountCompact(knownTotal)
: approxTotal !== null
? `≈ ${formatTokenCountCompact(approxTotal)}`
: formatIndependentFields(agent);
dt.kind === "exact"
? formatTokenCountCompact(dt.value)
: dt.kind === "approximate"
? `≈ ${formatTokenCountCompact(dt.value)}`
: "No usage reported";
return (
<button
@@ -313,34 +290,22 @@ function AgentUsageRow({
<span className="block truncate text-sm font-medium text-foreground">
{label}
</span>
{!unknown || approxTotal !== null ? (
{dt.kind !== "unknown" ? (
<Progress
aria-hidden="true"
className="mt-1.5 h-1.5"
value={
barTotal !== null && maxKnownTotal > 0n
? bigintRatio(barTotal, maxKnownTotal) * 100
maxDisplayValue > 0n
? bigintRatio(dt.value, maxDisplayValue) * 100
: null
}
/>
) : null}
</span>
<span className="flex shrink-0 items-center gap-2 text-sm text-muted-foreground">
{partial || ioPartial ? <Badge variant="outline">Partial</Badge> : null}
{dt.partial ? <Badge variant="outline">Partial</Badge> : null}
{trailing}
</span>
</button>
);
}
function formatIndependentFields(agent: AgentUsage): string {
const input = parseTokenCount(agent.usage.inputTokens.value);
const output = parseTokenCount(agent.usage.outputTokens.value);
if (input !== null || output !== null) {
const parts: string[] = [];
if (input !== null) parts.push(`in ${formatTokenCountCompact(input)}`);
if (output !== null) parts.push(`out ${formatTokenCountCompact(output)}`);
return parts.join(" · ");
}
return "No usage reported";
}
+6 -2
View File
@@ -816,9 +816,13 @@ test("focused view shows daily bars, coverage dates, and a partial explanation w
await expect(coverage).toContainText("reported turn");
// The partial explanation must appear when usage is known-incomplete.
// (explainPartial = hasUnknownUsage || invalidReportCount > 0 — both true here.)
// The seed has hasUnknownUsage=true AND invalidReportCount=1, so both
// per-condition caveat sentences must appear independently.
await expect(
page.getByTestId("agent-usage-focused-partial-explanation"),
page.getByTestId("agent-usage-focused-unknown-intervals-caveat"),
).toBeVisible();
await expect(
page.getByTestId("agent-usage-focused-invalid-reports-caveat"),
).toBeVisible();
});