- {head(t('stats.cost'), cost === null ? '—' : formatCost(cost, currency), costTip, costHref)}
- {/* The split rides only when a subagent subtree actually reported:
- without one the family figure IS the agent's own and two pills
- would repeat it. */}
- {subUsage !== null
- ? (
-
- {pill(t('stats.ownCost'), ownCost === null ? '—' : formatCost(ownCost, currency))}
- {pill(t('stats.subCost'), subCost === null ? '—' : formatCost(subCost, currency), '', subTip)}
-
- )
- : null}
+ {head(t('stats.team'), pair(familyTokens, costText), costTip, costHref)}
+ {/* The team ledger: one row per scope — the current agent itself,
+ then the subagent subtree (its session count from the same
+ fold). A scope with nothing billed reads 0 tokens / a dashed
+ cost (the price book's outage note lives in the tips). */}
+
+
+ {t('stats.currentAgent')}
+ {pair(ownTokens, ownText)}
+
+
+
+ {t('stats.teamSubs', { n: sub.count })}
+ ?
+
+ {pair(subTokens, subText)}
+ {subTip}
+
+
diff --git a/src/client/cost.ts b/src/client/cost.ts
index dcc2a75..2c8e586 100644
--- a/src/client/cost.ts
+++ b/src/client/cost.ts
@@ -302,6 +302,31 @@ export function estimateSessionCost(
return any ? toCurrency(total, currency) : null
}
+/**
+ * The scope's billed-token total: uncached input + cache read/write + output,
+ * summed over every billed model and pricing period — the token face of the
+ * same buckets the cost estimate prices. Hostile branches skip, the same
+ * re-proving the estimator applies.
+ */
+export function billedTokensOf(usage: SessionCostUsage | null | undefined): number {
+ if (usage === null || usage === undefined) return 0
+ let total = 0
+ for (const provider of Object.keys(usage)) {
+ const models = asRecord(usage[provider])
+ if (models === null) continue
+ for (const model of Object.keys(models)) {
+ const periods = asRecord(models[model])
+ if (periods === null) continue
+ for (const period of ['peak', 'off'] as const) {
+ const bucket = asRecord(periods[period])
+ if (bucket === null) continue
+ total += numOf(bucket.uncached) + numOf(bucket.cacheRead) + numOf(bucket.cacheWrite) + numOf(bucket.output)
+ }
+ }
+ }
+ return total
+}
+
/**
* Accumulate one usage's buckets into `out`, summing per (provider, model,
* period). Hostile branches skip (the same re-proving the estimator applies
diff --git a/src/client/i18n.ts b/src/client/i18n.ts
index 38f762f..29aa852 100644
--- a/src/client/i18n.ts
+++ b/src/client/i18n.ts
@@ -35,12 +35,14 @@ export const DICT_ZH: Record