feat: add TPS and cache hit rate to usage overview
This commit is contained in:
1 parent
a912dd473a
commit
3d2a7f357e
4 files changed
+47
-9
No files matched your search
@@ -127,6 +127,10 @@ export const zhCN = {
|
||||
'usage.stat.successRate': '成功率',
|
||||
'usage.stat.reasoningMeta': '思考 {tokens} Token',
|
||||
'usage.stat.averageLatency': '平均延迟',
|
||||
'usage.stat.tps': 'TPS',
|
||||
'usage.stat.performanceMeta': '{rpm} RPM · {tpm} TPM · 平均延迟 {latency} ms',
|
||||
'usage.stat.cacheHitRate': '缓存命中率',
|
||||
'usage.stat.cacheHitMeta': '命中 {hit} / 输入 {input} Token',
|
||||
'usage.trend.title': '请求与 Token 趋势',
|
||||
'usage.trend.description': '按系统本地小时聚合',
|
||||
'usage.token.title': 'Token 构成',
|
||||
@@ -942,6 +946,10 @@ export const en: Record<MessageKey, string> = {
|
||||
'usage.stat.successRate': 'Success Rate',
|
||||
'usage.stat.reasoningMeta': 'Reasoning {tokens} tokens',
|
||||
'usage.stat.averageLatency': 'Average Latency',
|
||||
'usage.stat.tps': 'TPS',
|
||||
'usage.stat.performanceMeta': '{rpm} RPM · {tpm} TPM · Avg latency {latency} ms',
|
||||
'usage.stat.cacheHitRate': 'Cache Hit Rate',
|
||||
'usage.stat.cacheHitMeta': '{hit} hit / {input} input tokens',
|
||||
'usage.trend.title': 'Request and Token Trend',
|
||||
'usage.trend.description': 'Grouped by local system hour',
|
||||
'usage.token.title': 'Token Breakdown',
|
||||
|
||||
@@ -35,7 +35,9 @@ type UsageOverview = {
|
||||
totalTokens: number;
|
||||
rpm: number;
|
||||
tpm: number;
|
||||
tps: number;
|
||||
averageLatencyMs: number;
|
||||
cacheHitRate: number;
|
||||
timeline: TimelinePoint[];
|
||||
};
|
||||
|
||||
@@ -342,7 +344,8 @@ function OverviewView({ overview }: { overview: UsageOverview }) {
|
||||
{ icon: Activity, label: t('usage.stat.requests'), value: compactNumber(overview.totalRequests), meta: t('usage.stat.requestMeta', { success: overview.successCount, failed: overview.failureCount }) },
|
||||
{ icon: Sparkles, label: t('usage.stat.tokens'), value: compactNumber(overview.totalTokens), meta: t('usage.stat.tokenMeta', { input: compactNumber(overview.inputTokens), output: compactNumber(overview.outputTokens) }) },
|
||||
{ icon: ShieldCheck, label: t('usage.stat.successRate'), value: `${overview.successRate.toFixed(1)}%`, meta: t('usage.stat.reasoningMeta', { tokens: compactNumber(overview.reasoningTokens) }) },
|
||||
{ icon: Clock3, label: t('usage.stat.averageLatency'), value: `${Math.round(overview.averageLatencyMs)} ms`, meta: `${overview.rpm.toFixed(2)} RPM · ${compactNumber(overview.tpm)} TPM` },
|
||||
{ icon: Clock3, label: t('usage.stat.tps'), value: `${overview.tps.toFixed(1)} TPS`, meta: t('usage.stat.performanceMeta', { rpm: overview.rpm.toFixed(2), tpm: compactNumber(overview.tpm), latency: Math.round(overview.averageLatencyMs) }) },
|
||||
{ icon: Database, label: t('usage.stat.cacheHitRate'), value: `${(overview.cacheHitRate * 100).toFixed(1)}%`, meta: t('usage.stat.cacheHitMeta', { hit: compactNumber(overview.cacheReadTokens), input: compactNumber(overview.inputTokens) }) },
|
||||
];
|
||||
return <div className="usage-overview-layout">
|
||||
<div className="usage-stat-grid">{cards.map(({ icon: Icon, label, value, meta }) => <article className="panel usage-stat-card" key={label}><span><Icon size={16} />{label}</span><strong>{value}</strong><small>{meta}</small></article>)}</div>
|
||||
|
||||
+3
-2
@@ -5218,7 +5218,7 @@ input:focus-visible {
|
||||
.usage-stat-grid {
|
||||
display: grid;
|
||||
grid-column: 1 / -1;
|
||||
grid-template-columns: repeat(auto-fit, minmax(min(180px, 100%), 1fr));
|
||||
grid-template-columns: repeat(5, minmax(0, 1fr));
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
@@ -5249,8 +5249,9 @@ input:focus-visible {
|
||||
overflow: hidden;
|
||||
color: #8a847c;
|
||||
font-size: 10px;
|
||||
line-height: 1.45;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
white-space: normal;
|
||||
}
|
||||
|
||||
.usage-trend-panel,
|
||||
|
||||
Reference in new issue
Block a user