fix: sort table

This commit is contained in:
Ephraim Atta-Duncan
2024-09-19 14:07:13 +00:00
parent 894e857826
commit 087d8bf150
6 changed files with 94 additions and 30 deletions

View File

@ -25,6 +25,8 @@ type LeaderboardTableProps = {
totalPages: number; totalPages: number;
perPage: number; perPage: number;
page: number; page: number;
sortBy: 'name' | 'createdAt' | 'signingVolume';
sortOrder: 'asc' | 'desc';
}; };
export const LeaderboardTable = ({ export const LeaderboardTable = ({
@ -32,6 +34,8 @@ export const LeaderboardTable = ({
totalPages, totalPages,
perPage, perPage,
page, page,
sortBy,
sortOrder,
}: LeaderboardTableProps) => { }: LeaderboardTableProps) => {
const { _ } = useLingui(); const { _ } = useLingui();
@ -49,10 +53,10 @@ export const LeaderboardTable = ({
size: 10, size: 10,
}, },
{ {
header: ({ column }) => ( header: () => (
<div <div
className="flex cursor-pointer items-center" className="flex cursor-pointer items-center"
onClick={() => column.toggleSorting(column.getIsSorted() === 'asc')} onClick={() => handleColumnSort('name', sortOrder)}
> >
{_(msg`Name`)} {_(msg`Name`)}
<CaretSortIcon className="ml-2 h-4 w-4" /> <CaretSortIcon className="ml-2 h-4 w-4" />
@ -63,10 +67,10 @@ export const LeaderboardTable = ({
size: 250, size: 250,
}, },
{ {
header: ({ column }) => ( header: () => (
<div <div
className="flex cursor-pointer items-center" className="flex cursor-pointer items-center"
onClick={() => column.toggleSorting(column.getIsSorted() === 'asc')} onClick={() => handleColumnSort('signingVolume', sortOrder)}
> >
{_(msg`Signing Volume`)} {_(msg`Signing Volume`)}
<CaretSortIcon className="ml-2 h-4 w-4" /> <CaretSortIcon className="ml-2 h-4 w-4" />
@ -76,11 +80,11 @@ export const LeaderboardTable = ({
cell: ({ row }) => <div>{Number(row.getValue('signingVolume'))}</div>, cell: ({ row }) => <div>{Number(row.getValue('signingVolume'))}</div>,
}, },
{ {
header: ({ column }) => { header: () => {
return ( return (
<div <div
className="flex cursor-pointer items-center" className="flex cursor-pointer items-center"
onClick={() => column.toggleSorting(column.getIsSorted() === 'asc')} onClick={() => handleColumnSort('createdAt', sortOrder)}
> >
{_(msg`Created`)} {_(msg`Created`)}
<CaretSortIcon className="ml-2 h-4 w-4" /> <CaretSortIcon className="ml-2 h-4 w-4" />
@ -91,7 +95,7 @@ export const LeaderboardTable = ({
cell: ({ row }) => <div>{row.original.createdAt.toLocaleDateString()}</div>, cell: ({ row }) => <div>{row.original.createdAt.toLocaleDateString()}</div>,
}, },
] satisfies DataTableColumnDef<SigningVolume>[]; ] satisfies DataTableColumnDef<SigningVolume>[];
}, []); }, [sortOrder]);
useEffect(() => { useEffect(() => {
startTransition(() => { startTransition(() => {
@ -117,6 +121,18 @@ export const LeaderboardTable = ({
setSearchString(e.target.value); setSearchString(e.target.value);
}; };
const handleColumnSort = (
column: 'name' | 'createdAt' | 'signingVolume',
sortOrder: 'asc' | 'desc',
) => {
startTransition(() => {
updateSearchParams({
sortBy: sortBy === column,
sortOrder: sortOrder === 'asc' ? 'desc' : 'asc',
});
});
};
return ( return (
<div className="relative"> <div className="relative">
<Input <Input

View File

@ -4,14 +4,22 @@ import { getRequiredServerComponentSession } from '@documenso/lib/next-auth/get-
import { isAdmin } from '@documenso/lib/next-auth/guards/is-admin'; import { isAdmin } from '@documenso/lib/next-auth/guards/is-admin';
import { getSigningVolume } from '@documenso/lib/server-only/admin/get-signing-volume'; import { getSigningVolume } from '@documenso/lib/server-only/admin/get-signing-volume';
export async function search(search: string, page: number, perPage: number) { type SearchOptions = {
search: string;
page: number;
perPage: number;
sortBy: 'name' | 'createdAt' | 'signingVolume';
sortOrder: 'asc' | 'desc';
};
export async function search({ search, page, perPage, sortBy, sortOrder }: SearchOptions) {
const { user } = await getRequiredServerComponentSession(); const { user } = await getRequiredServerComponentSession();
if (!isAdmin(user)) { if (!isAdmin(user)) {
throw new Error('Unauthorized'); throw new Error('Unauthorized');
} }
const results = await getSigningVolume({ search, page, perPage }); const results = await getSigningVolume({ search, page, perPage, sortBy, sortOrder });
return results; return results;
} }

View File

@ -12,6 +12,8 @@ type AdminLeaderboardProps = {
search?: string; search?: string;
page?: number; page?: number;
perPage?: number; perPage?: number;
sortBy?: 'name' | 'createdAt' | 'signingVolume';
sortOrder?: 'asc' | 'desc';
}; };
}; };
@ -27,9 +29,16 @@ export default async function Leaderboard({ searchParams = {} }: AdminLeaderboar
const page = Number(searchParams.page) || 1; const page = Number(searchParams.page) || 1;
const perPage = Number(searchParams.perPage) || 10; const perPage = Number(searchParams.perPage) || 10;
const searchString = searchParams.search || ''; const searchString = searchParams.search || '';
const sortBy = searchParams.sortBy || 'signingVolume';
const sortOrder = searchParams.sortOrder || 'desc';
// todo: change the name const { leaderboard: signingVolume, totalPages } = await search({
const { leaderboard: signingVolume, totalPages } = await search(searchString, page, perPage); search: searchString,
page,
perPage,
sortBy,
sortOrder,
});
return ( return (
<div> <div>
@ -42,6 +51,8 @@ export default async function Leaderboard({ searchParams = {} }: AdminLeaderboar
totalPages={totalPages} totalPages={totalPages}
page={page} page={page}
perPage={perPage} perPage={perPage}
sortBy={sortBy}
sortOrder={sortOrder}
/> />
</div> </div>
</div> </div>

View File

@ -12,12 +12,16 @@ export type GetSigningVolumeOptions = {
search?: string; search?: string;
page?: number; page?: number;
perPage?: number; perPage?: number;
sortBy?: 'name' | 'createdAt' | 'signingVolume';
sortOrder?: 'asc' | 'desc';
}; };
export async function getSigningVolume({ export async function getSigningVolume({
search = '', search = '',
page = 1, page = 1,
perPage = 10, perPage = 10,
sortBy = 'signingVolume',
sortOrder = 'desc',
}: GetSigningVolumeOptions) { }: GetSigningVolumeOptions) {
const whereClause = Prisma.validator<Prisma.SubscriptionWhereInput>()({ const whereClause = Prisma.validator<Prisma.SubscriptionWhereInput>()({
status: 'ACTIVE', status: 'ACTIVE',
@ -38,6 +42,8 @@ export async function getSigningVolume({
], ],
}); });
const orderBy = getOrderByClause({ sortBy, sortOrder });
const [subscriptions, totalCount] = await Promise.all([ const [subscriptions, totalCount] = await Promise.all([
prisma.subscription.findMany({ prisma.subscription.findMany({
where: whereClause, where: whereClause,
@ -76,15 +82,7 @@ export async function getSigningVolume({
}, },
}, },
}, },
orderBy: [ orderBy,
{
User: {
Document: {
_count: 'desc',
},
},
},
],
skip: Math.max(page - 1, 0) * perPage, skip: Math.max(page - 1, 0) * perPage,
take: perPage, take: perPage,
}), }),
@ -112,3 +110,34 @@ export async function getSigningVolume({
totalPages: Math.ceil(totalCount / perPage), totalPages: Math.ceil(totalCount / perPage),
}; };
} }
type GetOrderByClauseOptions = {
sortBy: string;
sortOrder: 'asc' | 'desc';
};
const getOrderByClause = ({ sortBy, sortOrder }: GetOrderByClauseOptions) => {
switch (sortBy) {
case 'name':
return [{ User: { name: sortOrder } }, { team: { name: sortOrder } }];
case 'createdAt':
return { createdAt: sortOrder };
default:
return [
{
User: {
Document: {
_count: sortOrder,
},
},
},
{
team: {
document: {
_count: sortOrder,
},
},
},
];
}
};

View File

@ -961,7 +961,7 @@ msgid "Create your account and start using state-of-the-art document signing. Op
msgstr "" msgstr ""
#: apps/web/src/app/(dashboard)/admin/documents/document-results.tsx:62 #: apps/web/src/app/(dashboard)/admin/documents/document-results.tsx:62
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:85 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:89
#: apps/web/src/app/(dashboard)/documents/[id]/document-page-view-information.tsx:35 #: apps/web/src/app/(dashboard)/documents/[id]/document-page-view-information.tsx:35
#: apps/web/src/app/(dashboard)/documents/data-table.tsx:54 #: apps/web/src/app/(dashboard)/documents/data-table.tsx:54
#: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table.tsx:65 #: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table.tsx:65
@ -1989,7 +1989,7 @@ msgid "My templates"
msgstr "" msgstr ""
#: apps/web/src/app/(dashboard)/admin/documents/[id]/recipient-item.tsx:148 #: apps/web/src/app/(dashboard)/admin/documents/[id]/recipient-item.tsx:148
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:57 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:61
#: apps/web/src/app/(dashboard)/admin/users/[id]/page.tsx:99 #: apps/web/src/app/(dashboard)/admin/users/[id]/page.tsx:99
#: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:66 #: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:66
#: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table-actions.tsx:144 #: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table-actions.tsx:144
@ -2594,7 +2594,7 @@ msgstr ""
msgid "Search by document title" msgid "Search by document title"
msgstr "" msgstr ""
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:125 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:141
#: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:144 #: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:144
msgid "Search by name or email" msgid "Search by name or email"
msgstr "" msgstr ""
@ -2816,8 +2816,8 @@ msgstr ""
msgid "Signing up..." msgid "Signing up..."
msgstr "" msgstr ""
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:71 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:75
#: apps/web/src/app/(dashboard)/admin/leaderboard/page.tsx:37 #: apps/web/src/app/(dashboard)/admin/leaderboard/page.tsx:46
msgid "Signing Volume" msgid "Signing Volume"
msgstr "" msgstr ""

View File

@ -956,7 +956,7 @@ msgid "Create your account and start using state-of-the-art document signing. Op
msgstr "Create your account and start using state-of-the-art document signing. Open and beautiful signing is within your grasp." msgstr "Create your account and start using state-of-the-art document signing. Open and beautiful signing is within your grasp."
#: apps/web/src/app/(dashboard)/admin/documents/document-results.tsx:62 #: apps/web/src/app/(dashboard)/admin/documents/document-results.tsx:62
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:85 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:89
#: apps/web/src/app/(dashboard)/documents/[id]/document-page-view-information.tsx:35 #: apps/web/src/app/(dashboard)/documents/[id]/document-page-view-information.tsx:35
#: apps/web/src/app/(dashboard)/documents/data-table.tsx:54 #: apps/web/src/app/(dashboard)/documents/data-table.tsx:54
#: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table.tsx:65 #: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table.tsx:65
@ -2007,7 +2007,7 @@ msgid "My templates"
msgstr "My templates" msgstr "My templates"
#: apps/web/src/app/(dashboard)/admin/documents/[id]/recipient-item.tsx:148 #: apps/web/src/app/(dashboard)/admin/documents/[id]/recipient-item.tsx:148
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:57 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:61
#: apps/web/src/app/(dashboard)/admin/users/[id]/page.tsx:99 #: apps/web/src/app/(dashboard)/admin/users/[id]/page.tsx:99
#: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:66 #: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:66
#: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table-actions.tsx:144 #: apps/web/src/app/(dashboard)/settings/security/passkeys/user-passkeys-data-table-actions.tsx:144
@ -2612,7 +2612,7 @@ msgstr "Search"
msgid "Search by document title" msgid "Search by document title"
msgstr "Search by document title" msgstr "Search by document title"
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:125 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:141
#: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:144 #: apps/web/src/app/(dashboard)/admin/users/data-table-users.tsx:144
msgid "Search by name or email" msgid "Search by name or email"
msgstr "Search by name or email" msgstr "Search by name or email"
@ -2838,8 +2838,8 @@ msgstr "Signing in..."
msgid "Signing up..." msgid "Signing up..."
msgstr "Signing up..." msgstr "Signing up..."
#: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:71 #: apps/web/src/app/(dashboard)/admin/leaderboard/data-table-leaderboard.tsx:75
#: apps/web/src/app/(dashboard)/admin/leaderboard/page.tsx:37 #: apps/web/src/app/(dashboard)/admin/leaderboard/page.tsx:46
msgid "Signing Volume" msgid "Signing Volume"
msgstr "Signing Volume" msgstr "Signing Volume"