Skip to content

feat(app): show RED metrics on the trace search results view - #2826

Open
alex-fedotyev wants to merge 1 commit into
mainfrom
alex/red-metrics-trace-search
Open

feat(app): show RED metrics on the trace search results view#2826
alex-fedotyev wants to merge 1 commit into
mainfrom
alex/red-metrics-trace-search

Conversation

@alex-fedotyev

@alex-fedotyev alex-fedotyev commented Aug 6, 2026

Copy link
Copy Markdown
Contributor

Summary

Trace search shows a single count histogram above the results. For trace sources in results mode, this replaces it with RED metrics:

  • Throughput counts spans (bars).
  • Errors toggles between rate (countIf(error) / count(), rendered as a percent line) and volume (countIf(error), bars).
  • Duration shows Avg, p95, and p99 over the source's raw duration column (line), with the unit applied at display from the source's precision.

Every aggregation is over a raw column (count, countIf, quantile/avg of the duration expression), so AggregatingMergeTree materialized views can satisfy the queries; ratio and unit conversion happen at the display layer or in a post-aggregation column.

The three charts are DBTimeCharts under a shared sync scope, so hovering one shows a synced cursor on all three at the same timestamp, and each renders as a dashboard-tile card. A RED/Heatmap switch in the search stats row flips the area to the same duration heatmap tile the dashboard renders.

Each chart is built from the same base config the histogram uses (in a small pure module, traceRedMetrics.ts), so they honor the active WHERE filter and selected time range. Logs and session sources keep the existing histogram.

This reuses existing building blocks (DBTimeChart, SegmentedControl, the chart-sync context, DBHeatmapChart + toHeatmapChartConfig, and the tile card header); no new chart or control primitives.

Screenshots

RED metrics, light

RED metrics, dark

Verified in both light and dark themes.

Test plan

  • Added unit tests for the aggregation builders (traceRedMetrics.test.ts); those plus the existing DBSearchPage suites pass under jest.
  • tsc --noEmit and eslint are clean.
  • Manually against a local stack: the RED trio renders for a trace source with a synced hover cursor across all three charts; the Errors Rate/Volume and RED/Heatmap switches work; a Logs source still shows the single histogram, unchanged. Empty, loading, and error states are inherited from DBTimeChart.
  • Verified at desktop width. The Errors header can wrap at very narrow widths, which I will tighten in a follow-up.

Notes

  • Adds a minor changeset.
  • An "add to dashboard" action from these charts is intentionally held for a follow-up PR.

@changeset-bot

changeset-bot Bot commented Aug 6, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 48f1a5a

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 3 packages
Name Type
@hyperdx/app Minor
@hyperdx/api Minor
@hyperdx/otel-collector Minor

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercel Bot commented Aug 6, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
hyperdx-oss Ready Ready Preview Aug 27, 2026 10:52pm
hyperdx-storybook Ready Ready Preview Aug 27, 2026 10:52pm

Request Review

@greptile-apps

greptile-apps Bot commented Aug 6, 2026

Copy link
Copy Markdown
Contributor

Greptile Summary

The PR replaces the trace-results histogram with synchronized throughput, error, and duration charts plus a duration heatmap option.

  • Builds MV-compatible error-rate aggregations from separate total and conditional counts.
  • Formats raw duration aggregations using the source precision.
  • Adds compact axis labels and bounded percentage-axis support to shared time charts.
  • Preserves the existing histogram for non-trace sources.

Confidence Score: 5/5

The PR appears safe to merge.

No blocking failure remains.

Important Files Changed

Filename Overview
packages/app/src/DBSearchPage.tsx Selects the RED or heatmap trace visualization while preserving the existing histogram for other sources.
packages/app/src/components/Search/TraceRedMetricsChart.tsx Composes synchronized metric tiles, hides error-rate helper series, and reuses the dashboard heatmap renderer.
packages/app/src/components/Search/traceRedMetrics.ts Builds throughput, error, and duration chart configurations while preserving raw-column aggregation.
packages/app/src/components/DBTimeChart.tsx Forwards compact x-axis and capped y-axis presentation options to the shared chart.
packages/app/src/HDXMultiSeriesTimeChart.tsx Adds inward-anchored compact time labels and bounded automatic y-axis scaling.
packages/app/src/components/Search/tests/traceRedMetrics.test.ts Covers the RED aggregation builders, filtering behavior, helper series, and duration formatting.
packages/app/src/tests/HDXMultiSeriesTimeChart.test.ts Covers compact tick anchoring and capped y-axis calculations.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart LR
  A[Trace search configuration] --> B{Chart mode}
  B -->|RED| C[Throughput: count spans]
  B -->|RED| D[Errors: count and conditional count]
  B -->|RED| E[Duration: avg, p95, p99]
  D --> F[Post-aggregation error rate]
  C --> G[Shared hover synchronization]
  F --> G
  E --> G
  B -->|Heatmap| H[Duration heatmap]
Loading

Reviews (11): Last reviewed commit: "feat(app): show RED metrics on the trace..." | Re-trigger Greptile

Comment thread packages/app/src/components/Search/traceRedMetrics.ts Outdated
@github-actions

github-actions Bot commented Aug 6, 2026

Copy link
Copy Markdown
Contributor

E2E Test Results

All tests passed • 322 passed • 1 skipped • 1302s

Status Count
✅ Passed 322
❌ Failed 0
⚠️ Flaky 1
⏭️ Skipped 1

Tests ran across 4 shards in parallel.

View full report →

@github-actions

github-actions Bot commented Aug 11, 2026

Copy link
Copy Markdown
Contributor

🟡 Tier 3 — Standard

Introduces new logic, modifies core functionality, or touches areas with non-trivial risk.

Why this tier:

  • Diff size: 629 production lines changed (Tier 2 max: < 250)

Review process: Full human review — logic, architecture, edge cases.
SLA: First-pass feedback within 1 business day.

Stats
  • Production files changed: 5
  • Production lines changed: 629 (+ 219 in test files, excluded from tier calculation)
  • Branch: alex/red-metrics-trace-search
  • Author: alex-fedotyev

To override this classification, remove the review/tier-3 label and apply a different review/tier-* label. Manual overrides are preserved on subsequent pushes.

@github-actions

github-actions Bot commented Aug 11, 2026

Copy link
Copy Markdown
Contributor

Deep Review

✅ No critical issues found.

This PR replaces the trace-search count histogram with RED metrics (Throughput / Errors / Duration) for trace sources that expose a duration column, adds a RED/Heatmap toggle, and introduces two small chart-axis primitives (cappedYAxisUpperBound, compactTickAnchor). The aggregation builders are pure and unit-tested, and the integration is guarded so logs/session sources keep the existing histogram.

The one substantive prior-review concern — that the error-rate chart used avg over a status boolean and would block AggregatingMergeTree materialized views — is resolved and verified: errorsConfig now aggregates count() (total_spans) and countIf(error) (error_spans) as separate MV-friendly series and divides them in a post-aggregation column (least(if(total_spans > 0, error_spans / total_spans, 0), 1)), hiding the helper counts. This mirrors the already-shipped, supported pattern in packages/app/src/components/ServiceDashboardEndpointSidePanel.tsx:125-142 (error_count / total_count as an aliased select item). The empty-bucket 0/0 and the >100% cases are guarded in the SQL, and the y-axis cap (yAxisMaxDomain=1) protects the rate axis from the large hidden count series.

🟡 P2 -- recommended

  • packages/app/src/components/Search/TraceRedMetricsChart.tsx:56 -- The new component and the DBSearchPage integration logic (source-eligibility gating via traceRedMetricsSource, the mode-reset effect, and the errors-tile-dropped branch when errorsConfig returns undefined) have no tests; only the pure aggregation builders are covered.
    • Fix: Add a rendering/integration test asserting that a trace source with a duration column shows the RED trio, a source without one falls back to the histogram, and a source with no status expression renders without the Errors tile.
🔵 P3 nitpicks (2)
  • packages/app/src/components/Search/TraceRedMetricsChart.tsx:91 -- durationFormat is a fresh object literal from getTraceDurationNumberFormat on every render and is a dependency of the duration useMemo, so durationConfig (and, similarly, the heatmap useMemo via the inline heatmapChartConfig object built in DBSearchPage) recomputes each render, defeating the memoization.
    • Fix: Memoize durationFormat (and the heatmapChartConfig object) on their primitive inputs so the config useMemos can actually cache.
  • packages/app/src/DBSearchPage.tsx:2589 -- The RED and histogram branches each repeat the Box container with className={searchPageStyles.timeChartContainer} and mih="0", differing only by the fixed h={240} and the child chart.
    • Fix: Hoist the shared container Box and switch only the inner chart to remove the duplication.

Reviewers (2): previous-comments, orchestrator synthesis (correctness, performance, maintainability, testing).

Testing gaps:

  • No coverage for the TraceRedMetricsChart component or the DBSearchPage source-eligibility / mode-reset / errors-tile-dropped branches.
  • The renderCompactXTick render path in HDXMultiSeriesTimeChart is exercised only indirectly; the anchor helper is unit-tested but the tick renderer itself is not.

For a trace source in results mode, replace the single count histogram above
the results with a Throughput / Errors / Duration trio:

- Throughput counts spans (bars). Duration shows Avg / p95 / p99 over the raw
  Duration column, with the unit applied at display from the source precision.
- Errors toggles between rate and volume. Rate is countIf/count as a percent
  line, capped at 100%. Volume groups error spans by status and renders them as
  bars, so clicking a bar filters the results to that status; this keeps the
  per-status drill-down the count histogram had.
- The three charts are DBTimeCharts under a shared sync scope (synced hover
  cursor) and use the dashboard tile card header. A RED/Heatmap switch in the
  stats row flips to the same heatmap tile the dashboard renders, and resets to
  RED when the source changes.
- Aggregations are over raw columns (count, countIf, quantile/avg) so
  materialized views can satisfy them; ratio and unit conversion happen at the
  display layer. Aggregation builders live in a pure, unit-tested module.
- Adds an opt-in compactXAxisLabels (edge-anchor first/last x labels) and
  yAxisMaxDomain (cap the y-axis while auto-scaling below it) to the shared
  time chart, both covered by focused unit tests.

Logs and session sources keep the existing histogram.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

review/tier-3 Standard — full human review required

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant