materialized view and a bit better ui
This commit is contained in:
1 parent
26b677154b
commit
49f9bb3458
30 files changed
+2184
-106
No files matched your search
@@ -190,3 +190,32 @@ export function sparklineSeries(issue: Issue, hours = 24): SparklineSeries {
|
||||
}
|
||||
return { points, max, reference: mean, breachIndex }
|
||||
}
|
||||
|
||||
/** One row per trace (all its samples grouped), plus one per traceless sample; newest first. */
|
||||
export interface SampleGroup {
|
||||
key: string
|
||||
traceId?: string
|
||||
samples: IssueSample[]
|
||||
firstTs: number
|
||||
}
|
||||
|
||||
export function groupSamplesByTrace(samples: IssueSample[]): SampleGroup[] {
|
||||
const byTrace = new Map<string, SampleGroup>()
|
||||
const out: SampleGroup[] = []
|
||||
samples.forEach((sample, i) => {
|
||||
if (!sample.traceId) {
|
||||
out.push({ key: `s-${sample.timestamp}-${i}`, samples: [sample], firstTs: sample.timestamp })
|
||||
return
|
||||
}
|
||||
const group = byTrace.get(sample.traceId)
|
||||
if (group) {
|
||||
group.samples.push(sample)
|
||||
group.firstTs = Math.min(group.firstTs, sample.timestamp)
|
||||
} else {
|
||||
const created = { key: sample.traceId, traceId: sample.traceId, samples: [sample], firstTs: sample.timestamp }
|
||||
byTrace.set(sample.traceId, created)
|
||||
out.push(created)
|
||||
}
|
||||
})
|
||||
return out.sort((a, b) => b.firstTs - a.firstTs)
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
import type { ProcessedTrace } from "../components/TraceVisualization"
|
||||
import type { TraceSummary } from "./types"
|
||||
|
||||
/** Same shape the server returns, derived from a fully loaded trace (for lists built from live data). */
|
||||
export function summarizeTrace(t: ProcessedTrace): TraceSummary {
|
||||
return {
|
||||
id: t.id,
|
||||
name: t.name,
|
||||
startTime: t.startTime,
|
||||
endTime: t.endTime,
|
||||
duration: t.duration,
|
||||
spanCount: t.spans.length,
|
||||
errorCount: t.errorCount,
|
||||
services: t.services,
|
||||
}
|
||||
}
|
||||
@@ -266,3 +266,36 @@ export interface ErrorStatsResponse {
|
||||
export interface ReleaseStatsResponse {
|
||||
series: Record<string, StatsPoint[]>;
|
||||
}
|
||||
|
||||
/** Per-trace rollup for overview tables (server-side, no spans). Times are unix ns. */
|
||||
export interface TraceSummary {
|
||||
id: string;
|
||||
name: string;
|
||||
startTime: number;
|
||||
endTime: number;
|
||||
duration: number;
|
||||
spanCount: number;
|
||||
errorCount: number;
|
||||
services: string[];
|
||||
}
|
||||
|
||||
/** One trace an issue occurred in, from GET /api/issues/:id/traces. */
|
||||
export interface IssueTrace {
|
||||
traceId: string;
|
||||
hits: number;
|
||||
firstSeen: number;
|
||||
lastSeen: number;
|
||||
summary?: TraceSummary;
|
||||
samples: IssueSample[];
|
||||
}
|
||||
|
||||
export interface IssueTracesResponse {
|
||||
issueId: string;
|
||||
totalOccurrences: number;
|
||||
traces: IssueTrace[];
|
||||
untraced: IssueSample[];
|
||||
hasMore: boolean;
|
||||
nextBefore?: number;
|
||||
/** false when the server only had the bounded in-memory samples. */
|
||||
complete: boolean;
|
||||
}
|
||||
Reference in new issue
Block a user