Add transaction rate and enhance chart tooltips

Added transaction-per-second (TPS) metric calculation to the TargetDetailPage and updated the chart to display it. Improved tooltip design and functionality for better readability, including dynamic metrics display and styled components.
This commit is contained in:
2026-02-12 11:04:38 +01:00
parent 5ab7ae1064
commit 8c94a30a81
2 changed files with 78 additions and 12 deletions

View File

@@ -36,6 +36,24 @@ function formatSeconds(value) {
return `${(value / 3600).toFixed(1)}h`;
}
function formatNumber(value, digits = 2) {
if (value === null || value === undefined || Number.isNaN(Number(value))) return "-";
return Number(value).toFixed(digits);
}
function MetricsTooltip({ active, payload, label }) {
if (!active || !payload || payload.length === 0) return null;
const row = payload[0]?.payload || {};
return (
<div className="chart-tooltip">
<div className="chart-tooltip-time">{label}</div>
<div className="chart-tooltip-item c1">connections: {formatNumber(row.connections, 0)}</div>
<div className="chart-tooltip-item c2">tps: {formatNumber(row.tps, 2)}</div>
<div className="chart-tooltip-item c3">cache: {formatNumber(row.cache, 2)}%</div>
</div>
);
}
async function loadMetric(targetId, metric, range, tokens, refresh) {
const { from, to } = toQueryRange(range);
return apiFetch(
@@ -91,13 +109,29 @@ export function TargetDetailPage() {
}, [id, range, tokens, refresh]);
const chartData = useMemo(
() =>
(series.connections || []).map((point, idx) => ({
ts: new Date(point.ts).toLocaleTimeString(),
connections: point.value,
xacts: series.xacts?.[idx]?.value || 0,
cache: series.cache?.[idx]?.value || 0,
})),
() => {
const con = series.connections || [];
const xacts = series.xacts || [];
const cache = series.cache || [];
return con.map((point, idx) => {
const prev = xacts[idx - 1];
const curr = xacts[idx];
let tps = 0;
if (prev && curr) {
const dt = (new Date(curr.ts).getTime() - new Date(prev.ts).getTime()) / 1000;
const dx = (curr.value || 0) - (prev.value || 0);
if (dt > 0 && dx >= 0) {
tps = dx / dt;
}
}
return {
ts: new Date(point.ts).toLocaleTimeString(),
connections: point.value,
tps,
cache: (cache[idx]?.value || 0) * 100,
};
});
},
[series]
);
@@ -232,11 +266,12 @@ export function TargetDetailPage() {
<ResponsiveContainer width="100%" height="85%">
<LineChart data={chartData}>
<XAxis dataKey="ts" hide />
<YAxis />
<Tooltip />
<Line type="monotone" dataKey="connections" stroke="#38bdf8" dot={false} />
<Line type="monotone" dataKey="xacts" stroke="#22c55e" dot={false} />
<Line type="monotone" dataKey="cache" stroke="#f59e0b" dot={false} />
<YAxis yAxisId="left" />
<YAxis yAxisId="right" orientation="right" domain={[0, 100]} />
<Tooltip content={<MetricsTooltip />} />
<Line yAxisId="left" type="monotone" dataKey="connections" stroke="#38bdf8" dot={false} strokeWidth={2} />
<Line yAxisId="left" type="monotone" dataKey="tps" stroke="#22c55e" dot={false} strokeWidth={2} />
<Line yAxisId="right" type="monotone" dataKey="cache" stroke="#f59e0b" dot={false} strokeWidth={2} />
</LineChart>
</ResponsiveContainer>
</div>

View File

@@ -359,6 +359,37 @@ td {
margin: 8px 0 0 18px;
}
.chart-tooltip {
background: #0f1934ee;
border: 1px solid #2f4a8b;
border-radius: 10px;
padding: 10px 12px;
min-width: 170px;
}
.chart-tooltip-time {
font-size: 12px;
color: #9cb2d8;
margin-bottom: 6px;
}
.chart-tooltip-item {
font-size: 14px;
margin: 3px 0;
}
.chart-tooltip-item.c1 {
color: #38bdf8;
}
.chart-tooltip-item.c2 {
color: #22c55e;
}
.chart-tooltip-item.c3 {
color: #f59e0b;
}
@media (max-width: 980px) {
body {
overflow: auto;