perf(stats): fold the dashboard's readings out of the statistics rollups - #281
Merged
Merged
Conversation
Every dashboard tick scanned 30 days of idx_query_logs_ts_metrics for its summary, and the top domain, client and upstream lists scanned their own indexes over 24 hours. Under the default retention those windows are the whole table, so the tick cost an index's length every 10 seconds. summary_multi_since, timeline_since, traffic_lists_since, domain_stats_since and top_upstreams_since now take every whole unit from the rollups and only the part of a unit their window starts inside from query_logs, in one statement. Nothing is read at the far end: the rollups are written with the rows, so the current unit is complete. timeline_since keeps counting the table when its bucket is finer than a quarter hour, which only happens while the log is a few hours old. Top upstreams now break ties by name, as the other lists do. Page misses, same database copies and BENCH_NOW as the baseline: - 370 677 rows: tick 3 408 -> 190, first response 3 117 -> 180, domain suggestions 3 973 -> 557, Statistics visit 7 937 -> 2 718 - 1 482 708 rows: tick 10 774 -> 227, first response 10 444 -> 215, domain suggestions 6 192 -> 559, Statistics visit 31 883 -> 11 641 No reading in any of the three benches got worse. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #281 +/- ##
==========================================
+ Coverage 91.30% 91.32% +0.02%
==========================================
Files 31 31
Lines 11587 11625 +38
==========================================
+ Hits 10579 10617 +38
Misses 1008 1008 ☔ View full report in Codecov by Harness. 🚀 New features to boost your workflow:
|
This was referenced Sep 14, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Every dashboard tick scanned 30 days of
idx_query_logs_ts_metricsfor its summary, and the top domain, client and upstream lists scanned their own indexes over 24 hours. Under the default retention those windows are the whole table, so a tick cost an index's length every 10 seconds.This moves those readings onto the rollups from #280.
summary_multi_since,timeline_since,traffic_lists_since,domain_stats_sinceandtop_upstreams_since.query_logsonly for the part of a unit its window starts inside, throughidx_query_logs_timestamp, in one statement. Nothing is read at the far end: the rollups are written in the same transaction as the rows, so the unit still filling up is complete.summary_multi_sincetells its three windows apart by which arm a table row came from. A row belongs to the one window whose partial quarter it fills; the wider windows count that quarter through the rollup.timeline_sincekeeps counting the table when its bucket is finer than a quarter hour, which only happens while the log is a few hours old.traffic_lists_sinceis shared with the Statistics page, so its two lists move too.stats_scan_sinceand the/api/stats/*metrics statements are the next PR.Page misses
All three benches on the same database copies and
BENCH_NOW=1789212354, before (db67506) and after. Every reading that changed is listed; the rest are identical.No reading in any of the three benches got worse.
idx_query_logs_ts_domain_clientandidx_query_logs_ts_upstreamnow serve nothing; they are dropped in the index-consolidation PR, once the Statistics scan has moved too.Tests
dashboard_readings_equal_a_recount_of_the_table(tests/stats_db_test.rs): three days of traffic starting 1 234 ms past an hour. Every reading is compared with the statement it replaced, run on the same rows, for windows starting before the data, on an hour, on a quarter, inside a quarter, inside an hour, and after the data. The timeline uses 60/600/1 800/3 600 s buckets, the lists use limits 5 and 1 000. On the old code, every comparison it reached matched until the top-upstream tie order, which the old statement left arbitrary.the_dashboard_readings_fold_rollups_rather_than_the_table(tests/stats_page_miss_test.rs): replaces three tests tied to the old indexes (the_dashboard_summary_is_one_metrics_scan,the_top_upstreams_never_read_the_log_table,a_short_window_reads_a_short_stretch_of_the_traffic_lists). Each reading must cost under a tenth of a scan over every row. Before the implementation it failed withsummary read 107 pages where a scan over every row reads 168.the_traffic_lists_are_covered_by_their_index(src/db.rs), which asserted the plan of a statement that no longer exists.Test plan
cargo fmt --checkcargo clippy --all-targets -- -D warningscargo nextest run: 681 passed, 8 skippedcd e2e && cargo test --test specs: all spec cases passedcd e2e && cargo test --test e2e: 17 scenarios (17 passed), 85 steps (85 passed)🤖 Generated with Claude Code