fix: function templates pagination

This commit is contained in:
Arman
2025-04-01 11:11:24 +02:00
parent f907e0b5a6
commit 008f4e346d
2 changed files with 78 additions and 85 deletions
@@ -2,7 +2,7 @@
import { goto } from '$app/navigation';
import { base } from '$app/paths';
import { page } from '$app/stores';
import { EmptyFilter, EmptySearch, SearchQuery, SvgIcon } from '$lib/components';
import { EmptyFilter, EmptySearch, Paginator, SearchQuery, SvgIcon } from '$lib/components';
import { Button } from '$lib/elements/forms';
import { Container, ContainerButton } from '$lib/layout';
import { isServiceLimited } from '$lib/stores/billing';
@@ -23,7 +23,6 @@
import Card from '$lib/components/card.svelte';
import Link from '$lib/elements/link.svelte';
import Avatar from '$lib/components/avatar.svelte';
import PaginationWithLimit from '$lib/components/paginationWithLimit.svelte';
import { getIconFromRuntime } from '$lib/stores/runtimes';
export let data;
@@ -140,86 +139,88 @@
</Card>
</Layout.Stack>
<Layout.Stack gap="l">
{#if data.templates.length > 0}
<Layout.Grid columns={2} columnsXL={3} columnsXS={1}>
{#each data.templates as template}
{@const baseRuntimes = getBaseRuntimes(template.runtimes)}
{@const displayed = baseRuntimes.slice(0, 2)}
{@const hidden = baseRuntimes.slice(1, -1)}
<PinkCard.Base radius="m" padding="xs">
<Layout.Stack height="100%" justifyContent="space-between" gap="xl">
<Layout.Stack gap="xxxs">
<Typography.Text
variant="m-500"
color="--fgcolor-neutral-primary">
{template.name}
</Typography.Text>
{#if data.templates?.length > 0}
<Paginator
items={data.templates}
let:paginatedItems
limit={12}
hidePages={false}
hasLimit>
<Layout.Grid columns={2} columnsXL={3} columnsXS={1}>
{#each paginatedItems as template}
{@const baseRuntimes = getBaseRuntimes(template.runtimes)}
{@const displayed = baseRuntimes.slice(0, 2)}
{@const hidden = baseRuntimes.slice(1, -1)}
<PinkCard.Base radius="m" padding="xs">
<Layout.Stack height="100%" justifyContent="space-between" gap="xl">
<Layout.Stack gap="xxxs">
<Typography.Text
variant="m-500"
color="--fgcolor-neutral-primary">
{template.name}
</Typography.Text>
<Typography.Text variant="m-400">
{template.tagline}
</Typography.Text>
</Layout.Stack>
<Typography.Text variant="m-400">
{template.tagline}
</Typography.Text>
</Layout.Stack>
<Layout.Stack
direction="row"
justifyContent="space-between"
alignItems="center">
<AvatarGroup>
{#each displayed as runtime}
{@const icon = getIconFromRuntime(runtime.name)}
{#if icon}
<Avatar alt={runtime.name} size="xs">
<SvgIcon name={icon} iconSize="small" />
</Avatar>
{/if}
{/each}
{#if hidden.length}
<Tooltip>
<Avatar alt="hidden runtime number" size="xs">
<span style:font-size="10px">
+{hidden.length}
</span>
</Avatar>
<span slot="tooltip">
{hidden.map((n) => n.name).join(', ')}
</span>
</Tooltip>
{/if}
</AvatarGroup>
<Layout.Stack
direction="row"
gap="s"
alignItems="center"
inline>
<Button
href={`${base}/project-${$page.params.project}/functions/templates/template-${template.id}`}
text>
<span class="text">Details</span>
</Button>
{#if $canWriteFunctions}
<ContainerButton
title="functions"
disabled={buttonDisabled}
buttonType="secondary"
buttonHref={`${base}/project-${$page.params.project}/functions/create-function/template-${template.id}`}
showIcon={false}
buttonText="Create"
buttonEventData={{
source: 'functions_template'
}}
buttonEvent="create_function" />
{/if}
justifyContent="space-between"
alignItems="center">
<AvatarGroup>
{#each displayed as runtime}
{@const icon = getIconFromRuntime(runtime.name)}
{#if icon}
<Avatar alt={runtime.name} size="xs">
<SvgIcon name={icon} iconSize="small" />
</Avatar>
{/if}
{/each}
{#if hidden.length}
<Tooltip>
<Avatar alt="hidden runtime number" size="xs">
<span style:font-size="10px">
+{hidden.length}
</span>
</Avatar>
<span slot="tooltip">
{hidden.map((n) => n.name).join(', ')}
</span>
</Tooltip>
{/if}
</AvatarGroup>
<Layout.Stack
direction="row"
gap="s"
alignItems="center"
inline>
<Button
href={`${base}/project-${$page.params.project}/functions/templates/template-${template.id}`}
text>
<span class="text">Details</span>
</Button>
{#if $canWriteFunctions}
<ContainerButton
title="functions"
disabled={buttonDisabled}
buttonType="secondary"
buttonHref={`${base}/project-${$page.params.project}/functions/create-function/template-${template.id}`}
showIcon={false}
buttonText="Create"
buttonEventData={{
source: 'functions_template'
}}
buttonEvent="create_function" />
{/if}
</Layout.Stack>
</Layout.Stack>
</Layout.Stack>
</Layout.Stack>
</PinkCard.Base>
{/each}
</Layout.Grid>
<PaginationWithLimit
name="Templates"
limit={data.limit}
offset={data.offset}
total={data.sum} />
</PinkCard.Base>
{/each}
</Layout.Grid>
</Paginator>
{:else if data?.search}
<EmptySearch hidePagination search={data.search}>
<Button secondary on:click={clearSearch}>Clear search</Button>
@@ -6,11 +6,7 @@ import type { PageLoad } from './$types';
export const load: PageLoad = async ({ url, route, depends, parent }) => {
depends(Dependencies.FUNCTIONS);
const limit = getLimit(url, route, PAGE_LIMIT);
const page = getPage(url);
const search = getSearch(url);
const view = getView(url, route, View.Grid);
const offset = pageToOffset(page, limit);
const filter = {
useCases: url.searchParams.getAll('useCase'),
runtimes: url.searchParams.getAll('runtime')
@@ -51,15 +47,11 @@ export const load: PageLoad = async ({ url, route, depends, parent }) => {
});
return {
offset,
limit,
view,
filter,
runtimes,
useCases,
search,
sum: templates.length,
templates: templates.splice(((page === 0 ? 1 : page) - 1) * limit, limit),
templates,
functions: await sdk.forProject.functions.list()
};
};