fix(usage-chart): stack flat_cost on Team Usage's Daily Spend chart

The Team Usage view's Daily Spend chart previously visualized only per-request
spend, so a team with sizeable PTU flat cost saw the Flat Cost card show a large
aggregate while the per-day bars stayed flat at fractional cents. Backend data
was correct; this was a chart-only readability gap.

Bars now stack Request spend (cyan) on top of Flat cost (violet), with the
legend on so the two series are labeled. The custom tooltip splits into three
lines: Request spend, Flat cost, Total cost. Data is projected to friendly
top-level keys before it hits the chart so the legend reads "Flat cost" and
"Request spend" instead of "metrics.spend" / "metrics.flat_cost".

Scope is Team Usage only, matching where flat_cost is exposed today. Global
Usage / Project Spend view does not surface flat_cost and is intentionally
untouched.
This commit is contained in:
Yucheng Zhu 2026-07-21 11:53:28 -07:00
parent b69f3601f8
commit 5808dcf079

View file

@ -582,25 +582,33 @@ const EntityUsage: React.FC<EntityUsageProps> = ({ accessToken, entityType, enti
</CardHeader>
<CardContent>
<BarChart
data={[...spendData.results].sort(
(a, b) => new Date(a.date).getTime() - new Date(b.date).getTime(),
)}
data={[...spendData.results]
.sort((a, b) => new Date(a.date).getTime() - new Date(b.date).getTime())
.map((row) => ({
...row,
"Request spend": row.metrics.spend ?? 0,
"Flat cost": row.metrics.flat_cost ?? 0,
}))}
index="date"
categories={["metrics.spend"]}
colors={["cyan"]}
categories={["Request spend", "Flat cost"]}
colors={["cyan", "violet"]}
stack={true}
valueFormatter={valueFormatterSpend}
yAxisWidth={100}
showLegend={false}
showLegend={true}
customTooltip={({ payload, active }) => {
if (!active || !payload?.[0]) return null;
const data = payload[0].payload;
const entityCount = Object.keys(data.breakdown.entities || {}).length;
const requestSpend = data.metrics.spend ?? 0;
const flatCost = data.metrics.flat_cost ?? 0;
const totalCost = requestSpend + flatCost;
return (
<div className="bg-white p-4 shadow-lg rounded-lg border">
<p className="font-bold">{data.date}</p>
<p className="text-cyan-500">
Total Spend: ${formatNumberWithCommas(data.metrics.spend, 2)}
</p>
<p className="text-cyan-500">Request spend: ${formatNumberWithCommas(requestSpend, 2)}</p>
<p className="text-violet-500">Flat cost: ${formatNumberWithCommas(flatCost, 2)}</p>
<p className="font-semibold">Total cost: ${formatNumberWithCommas(totalCost, 2)}</p>
<p className="text-gray-600">Total Requests: {data.metrics.api_requests}</p>
<p className="text-gray-600">Successful: {data.metrics.successful_requests}</p>
<p className="text-gray-600">Failed: {data.metrics.failed_requests}</p>