|
1 | 1 | <template> |
2 | 2 | <div> |
3 | | - <DataTable :value="summaryTable" tableStyle="min-width: 50rem;" scrollable scrollHeight="800px" showGridlines |
| 3 | + <DataTable :value="data" tableStyle="min-width: 50rem;" scrollable scrollHeight="800px" showGridlines |
4 | 4 | selectionMode="single" v-model:selection="selectedPkg" v-model:filters="filters" |
5 | 5 | :globalFilterFields="['user', 'repo', 'pkg', 'description', 'categories', 'os_categories']" removableSort |
6 | 6 | sortMode="multiple" paginator :rows="10" :rowsPerPageOptions="[5, 10, 20, 50, 100, 200, 1000]"> |
7 | 7 |
|
8 | 8 | <template #header> |
9 | | - <div style="display: flex; justify-content: center; "> |
10 | | - <div style="width: 50%"> |
| 9 | + <div style="display: flex; justify-content: space-between;"> |
| 10 | + <div> |
| 11 | + <MultiSelect v-model="selectedCategories" display="chip" :options="categories" filter :maxSelectedLabels="4" |
| 12 | + placeholder="Select Categories" /> |
| 13 | + </div> |
| 14 | + |
| 15 | + <div style="width: 40%"> |
11 | 16 | <IconField> |
12 | 17 | <InputIcon> |
13 | 18 | <i class="pi pi-search" /> |
14 | 19 | </InputIcon> |
15 | 20 | <InputText style="width: 100%" v-model="filters['global'].value" placeholder="Global Search" /> |
16 | 21 | </IconField> |
17 | 22 | </div> |
| 23 | + |
18 | 24 | </div> |
19 | 25 | </template> |
20 | 26 |
|
|
26 | 32 | <Column sortable field="version" header="Version" style="text-align: center;" /> |
27 | 33 | <Column sortable field="dependencies" header="Depen-dencies" style="text-align: center;" /> |
28 | 34 |
|
29 | | - <Column sortable field="testcases" header="TestCases" style="text-align: center;" /> |
| 35 | + <Column sortable field="testcases" header="Test Cases" style="text-align: center;" /> |
30 | 36 |
|
31 | 37 | <Column sortable field="tests" header="Tests" style="text-align: center;" /> |
32 | 38 | <Column sortable field="examples" header="Examples" style="text-align: center;" /> |
|
103 | 109 | <script setup lang="ts"> |
104 | 110 | import type { Pkg, PkgInfo, Test } from '~/shared/info'; |
105 | 111 | import { FilterMatchMode } from '@primevue/core/api'; |
| 112 | +import type { Summary } from '~/shared/workflows'; |
106 | 113 |
|
107 | 114 | // interactive filter/search inputs |
108 | 115 | const filters = ref<any>({ |
@@ -134,7 +141,7 @@ const summaryColumns = [ |
134 | 141 | // { field: "os_categories", header: "OS Categories" }, |
135 | 142 | ]; |
136 | 143 |
|
137 | | -const summaryTable = computed(() => { |
| 144 | +const summaryTable = computed<SummaryTable[]>(() => { |
138 | 145 | const value = summaries.value.map(val => { |
139 | 146 | return Object.entries(val.pkgs).map(([name, pkg]) => { |
140 | 147 | return { |
@@ -183,7 +190,20 @@ const summaryTable = computed(() => { |
183 | 190 | }); |
184 | 191 | }); |
185 | 192 |
|
| 193 | +type SummaryTable = { idx: number; user: string; repo: string; pkg: string; version: string; dependencies: number | null; testcases: number | null; tests: number | null; examples: number | null; benches: number | null; author: string[] | null; description: string[]; categories: string[] | null; os_categories: string[] | null; }; |
| 194 | +const data = ref<SummaryTable[]>([]); |
| 195 | +watch(summaryTable, (val) => data.value = val); |
| 196 | +
|
| 197 | +const categories = computed(() => [...new Set(summaryTable.value.map(val => val.categories).flat().filter(c => c))].sort()); |
| 198 | +const selectedCategories = ref<string[]>([]); |
| 199 | +watch(selectedCategories, cat => { |
| 200 | + if (cat.length === 0) { |
| 201 | + data.value = summaryTable.value; |
| 202 | + return; |
| 203 | + } |
186 | 204 |
|
| 205 | + data.value = summaryTable.value.filter(val => cat.find(c => val.categories?.find(vc => vc === c))); |
| 206 | +}); |
187 | 207 |
|
188 | 208 | const dialogShow = ref(false); |
189 | 209 | const dialogHeader = ref<{ repo: string, repo_url: string, pkg_name: string, pkg: Pkg } | null>(); |
|
0 commit comments