Skip to content
This repository was archived by the owner on May 28, 2025. It is now read-only.

Commit d7642fe

Browse files
committed
Add basic filters to runtime comparison page
The filters are actually synchronized, because they share some name of properties. When the filter changes, the URL is updated, and then when a tab is changed, it reloads the filter from the URL.
1 parent 2710eae commit d7642fe

File tree

2 files changed

+171
-1
lines changed

2 files changed

+171
-1
lines changed
Lines changed: 130 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,130 @@
1+
<script setup lang="ts">
2+
import Toggle from "../toggle.vue";
3+
import Tooltip from "../tooltip.vue";
4+
import {ref, toRaw, watch} from "vue";
5+
import {deepCopy} from "../../../utils/copy";
6+
import {PREF_FILTERS_OPENED} from "../prefs";
7+
import {createPersistedRef} from "../../../storage";
8+
import {RuntimeBenchmarkFilter} from "./common";
9+
10+
const props = defineProps<{
11+
// When reset, set filter to this value
12+
defaultFilter: RuntimeBenchmarkFilter;
13+
// Initialize the filter with this value
14+
initialFilter: RuntimeBenchmarkFilter;
15+
}>();
16+
const emit = defineEmits<{
17+
(e: "change", filter: RuntimeBenchmarkFilter): void;
18+
(e: "export"): void;
19+
}>();
20+
21+
function reset() {
22+
// We must not change the default filter
23+
filter.value = deepCopy(props.defaultFilter);
24+
}
25+
26+
let filter = ref(deepCopy(props.initialFilter));
27+
watch(
28+
filter,
29+
(newValue, _) => {
30+
emit("change", toRaw(newValue));
31+
},
32+
{deep: true}
33+
);
34+
35+
const opened = createPersistedRef(PREF_FILTERS_OPENED);
36+
</script>
37+
38+
<template>
39+
<fieldset class="collapsible-section">
40+
<Toggle :opened="opened" @change="(value) => (opened = value)">
41+
<template #label>Filters</template>
42+
<template #content>
43+
<div>
44+
<div class="section">
45+
<div class="section-heading">Filter</div>
46+
<input id="filter" type="text" v-model="filter.name" />
47+
</div>
48+
<div class="section">
49+
<div class="section-heading">
50+
<span>Show non-relevant results</span>
51+
<Tooltip>
52+
Whether to show test case results that are not relevant (i.e.,
53+
not significant or have a large enough magnitude). You can see
54+
<a
55+
href="https://github.com/rust-lang/rustc-perf/blob/master/docs/comparison-analysis.md#how-is-relevance-of-a-test-run-summary-determined"
56+
>
57+
here</a
58+
>
59+
how relevance is calculated.
60+
</Tooltip>
61+
</div>
62+
<input
63+
type="checkbox"
64+
v-model="filter.nonRelevant"
65+
style="margin-left: 20px"
66+
/>
67+
</div>
68+
<div class="section">
69+
<div class="section-heading">
70+
<span>Display raw data</span>
71+
<Tooltip>Whether to display or not raw data columns.</Tooltip>
72+
</div>
73+
<input
74+
type="checkbox"
75+
v-model="filter.showRawData"
76+
style="margin-left: 20px"
77+
/>
78+
</div>
79+
<button @click="reset" style="margin-right: 10px">
80+
Reset filters
81+
</button>
82+
</div>
83+
</template>
84+
</Toggle>
85+
</fieldset>
86+
</template>
87+
88+
<style scoped lang="scss">
89+
.section-heading {
90+
font-size: 16px;
91+
}
92+
93+
#filter {
94+
margin-left: 52px;
95+
}
96+
97+
.states-list {
98+
display: flex;
99+
flex-direction: column;
100+
align-items: start;
101+
list-style: none;
102+
margin: 0;
103+
padding: 0;
104+
}
105+
106+
.section-list-wrapper {
107+
flex-direction: column;
108+
}
109+
110+
@media (min-width: 760px) {
111+
.states-list {
112+
justify-content: start;
113+
flex-direction: row;
114+
align-items: center;
115+
width: 80%;
116+
}
117+
118+
.section-list-wrapper {
119+
flex-direction: row;
120+
}
121+
}
122+
123+
.states-list > li {
124+
margin-right: 15px;
125+
}
126+
127+
.cache-label {
128+
font-weight: bold;
129+
}
130+
</style>

site/frontend/src/pages/compare/runtime/runtime-page.vue

Lines changed: 41 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,8 @@ import {BenchmarkInfo} from "../../../api";
1313
import {importantRuntimeMetrics} from "../metrics";
1414
import ComparisonsTable from "./comparisons-table.vue";
1515
import {getBoolOrDefault} from "../shared";
16-
import {getUrlParams} from "../../../utils/navigation";
16+
import {changeUrl, getUrlParams} from "../../../utils/navigation";
17+
import Filters from "./filters.vue";
1718
1819
const props = defineProps<{
1920
data: CompareResponse;
@@ -40,6 +41,40 @@ function loadFilterFromUrl(
4041
};
4142
}
4243
44+
/**
45+
* Stores the given filter parameters into URL, so that the current "view" can be shared with
46+
* others easily.
47+
*/
48+
function storeFilterToUrl(
49+
filter: RuntimeBenchmarkFilter,
50+
defaultFilter: RuntimeBenchmarkFilter,
51+
urlParams: Dict<string>
52+
) {
53+
function storeOrReset<T extends boolean | string>(
54+
name: string,
55+
value: T,
56+
defaultValue: T
57+
) {
58+
if (value === defaultValue) {
59+
if (urlParams.hasOwnProperty(name)) {
60+
delete urlParams[name];
61+
}
62+
} else {
63+
urlParams[name] = value.toString();
64+
}
65+
}
66+
67+
storeOrReset("name", filter.name || null, defaultFilter.name);
68+
storeOrReset("nonRelevant", filter.nonRelevant, defaultFilter.nonRelevant);
69+
storeOrReset("showRawData", filter.showRawData, defaultFilter.showRawData);
70+
changeUrl(urlParams);
71+
}
72+
73+
function updateFilter(newFilter: RuntimeBenchmarkFilter) {
74+
storeFilterToUrl(newFilter, defaultRuntimeFilter, getUrlParams());
75+
filter.value = newFilter;
76+
}
77+
4378
const urlParams = getUrlParams();
4479
const filter = ref(loadFilterFromUrl(urlParams, defaultRuntimeFilter));
4580
@@ -61,6 +96,11 @@ const filteredSummary = computed(() => computeSummary(comparisons.value));
6196
:benchmark-info="benchmarkInfo"
6297
:quick-links="importantRuntimeMetrics"
6398
/>
99+
<Filters
100+
:defaultFilter="defaultRuntimeFilter"
101+
:initialFilter="filter"
102+
@change="updateFilter"
103+
/>
64104
<OverallSummary :summary="filteredSummary" />
65105
<ComparisonsTable
66106
:comparisons="comparisons"

0 commit comments

Comments
 (0)