-
Notifications
You must be signed in to change notification settings - Fork 71
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
add filtering to api pagination #2130
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change | ||||||
---|---|---|---|---|---|---|---|---|
@@ -1,9 +1,11 @@ | ||||||||
<script lang="ts"> | ||||||||
import type { HTMLAttributes } from 'svelte/elements'; | ||||||||
|
||||||||
import debounce from 'just-debounce'; | ||||||||
import { onMount } from 'svelte'; | ||||||||
|
||||||||
import Alert from '$lib/holocene/alert.svelte'; | ||||||||
import Input from '$lib/holocene/input/input.svelte'; | ||||||||
import FilterSelect from '$lib/holocene/select/filter-select.svelte'; | ||||||||
import SkeletonTable from '$lib/holocene/skeleton/table.svelte'; | ||||||||
import { | ||||||||
|
@@ -29,11 +31,14 @@ | |||||||
itemsKeyname?: string; | ||||||||
previousButtonLabel: string; | ||||||||
nextButtonLabel: string; | ||||||||
filterable?: boolean | undefined; | ||||||||
filterInputLabel?: string | undefined; | ||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Since the input only shows up if |
||||||||
} | ||||||||
|
||||||||
type PaginatedRequest<T> = ( | ||||||||
size: number, | ||||||||
token: string, | ||||||||
query?: string, | ||||||||
) => Promise<{ items: T[]; nextPageToken: string }>; | ||||||||
|
||||||||
export let onError: (error: Error) => void | undefined = undefined; | ||||||||
|
@@ -52,6 +57,10 @@ | |||||||
export let itemsKeyname = 'items'; | ||||||||
export let previousButtonLabel: string; | ||||||||
export let nextButtonLabel: string; | ||||||||
export let filterable = false; | ||||||||
export let filterInputLabel: string = undefined; | ||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. What do you think about making this ⬇️ instead?
Suggested change
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I could be talked into just using There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||||||||
|
||||||||
let query = ''; | ||||||||
|
||||||||
let store: PaginationStore<T> = createPaginationStore( | ||||||||
pageSizeOptions, | ||||||||
|
@@ -157,6 +166,22 @@ | |||||||
break; | ||||||||
} | ||||||||
} | ||||||||
|
||||||||
const handleFilter = async () => { | ||||||||
clearError(); | ||||||||
store.reset(); | ||||||||
store.setUpdating(); | ||||||||
try { | ||||||||
const fetchItems = await onFetch(); | ||||||||
const response = await fetchItems($store.pageSize, '', query); | ||||||||
const { nextPageToken } = response; | ||||||||
const items = response[itemsKeyname] || []; | ||||||||
store.nextPageWithItems(nextPageToken, items); | ||||||||
} catch (err) { | ||||||||
error = err; | ||||||||
if (onError) onError(error); | ||||||||
} | ||||||||
}; | ||||||||
</script> | ||||||||
|
||||||||
<svelte:window on:keydown={handleKeydown} /> | ||||||||
|
@@ -175,11 +200,27 @@ | |||||||
<slot name="header" visibleItems={$store.visibleItems} /> | ||||||||
<div class="relative mb-8 flex flex-col gap-4"> | ||||||||
<div class="flex flex-col items-center justify-between gap-4 lg:flex-row"> | ||||||||
<div class="flex items-center gap-1 lg:gap-2 xl:gap-3"> | ||||||||
<slot name="action-top-left" visibleItems={$store.visibleItems} /> | ||||||||
</div> | ||||||||
{#if $$slots['action-top-left']} | ||||||||
<div class="flex shrink-0 items-center gap-1 lg:gap-2 xl:gap-3"> | ||||||||
<slot name="action-top-left" visibleItems={$store.visibleItems} /> | ||||||||
</div> | ||||||||
{/if} | ||||||||
{#if filterable && filterInputLabel} | ||||||||
<Input | ||||||||
id="api-pagination-search-input" | ||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Do we want a search icon here, similar to our other "search" inputs?
Suggested change
|
||||||||
class="grow" | ||||||||
bind:value={query} | ||||||||
slot="action-top-left" | ||||||||
label={filterInputLabel} | ||||||||
labelHidden | ||||||||
placeholder={filterInputLabel} | ||||||||
on:input={debounce(handleFilter, 1000)} | ||||||||
on:clear={handleFilter} | ||||||||
clearable | ||||||||
/> | ||||||||
{/if} | ||||||||
<nav | ||||||||
class="flex flex-col justify-end gap-4 md:flex-row" | ||||||||
class="flex shrink-0 flex-col justify-end gap-4 md:flex-row" | ||||||||
aria-label="{$$restProps['aria-label']} 1" | ||||||||
> | ||||||||
<slot name="action-top-center" /> | ||||||||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We should replace the custom input on the Schedules page ⬇️ with this prop 🎉
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We should, I can make a follow up task for that