create reusable query render wrapper that handles loading and error states
This commit is contained in:
parent
9074f79dee
commit
1566be88f6
34
src/components/LoadingWrapper.tsx
Normal file
34
src/components/LoadingWrapper.tsx
Normal file
@ -0,0 +1,34 @@
|
||||
import { type UseTRPCQueryResult } from "@trpc/react-query/shared";
|
||||
import { LoadingBarChart } from "./LoadingBarChart";
|
||||
import { ErrorNotice } from "./notice";
|
||||
|
||||
/**
|
||||
* Generic query wrapper which handles the states of a query
|
||||
* (loading, error, etc.). Will hydrate child with query.data
|
||||
*
|
||||
*/
|
||||
export function QueryWaitWrapper<TData, TError>({
|
||||
query,
|
||||
Render,
|
||||
}: {
|
||||
query: UseTRPCQueryResult<TData, TError>;
|
||||
Render: (data: TData) => JSX.Element;
|
||||
}) {
|
||||
if (query.isLoading) {
|
||||
return <LoadingBarChart width={200} height={200} />;
|
||||
}
|
||||
|
||||
if (!query.data || query.isError) {
|
||||
return (
|
||||
<div className="my-10 sm:my-16 md:my-28">
|
||||
<ErrorNotice
|
||||
icon
|
||||
header="Unable to retrieve page data. Please try again."
|
||||
body="If this issue persists, please contact a site administrator"
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
return <Render {...query.data} />;
|
||||
}
|
@ -5,9 +5,9 @@ import { useRouter } from "next/router";
|
||||
import ResourceTable from "~/components/ResourceTable";
|
||||
import { api } from "~/utils/api";
|
||||
import { parseQueryData } from "~/utils/parseSearchForm";
|
||||
import { LoadingBarChart } from "~/components/LoadingBarChart";
|
||||
import { ErrorNotice } from "~/components/notice";
|
||||
import { HeaderFooterLayout } from "~/layouts/HeaderFooterLayout";
|
||||
import { type AuditoryResource } from "@prisma/client";
|
||||
import { QueryWaitWrapper } from "~/components/LoadingWrapper";
|
||||
|
||||
const Resources = () => {
|
||||
const router = useRouter();
|
||||
@ -30,29 +30,16 @@ const Resources = () => {
|
||||
: "";
|
||||
const printLink = `${router.route}/print?${printQueryStr}`;
|
||||
|
||||
const ConditionalTable = () => {
|
||||
if (resourceQuery.isLoading) {
|
||||
return <LoadingBarChart width={200} height={200} />;
|
||||
}
|
||||
|
||||
if (!resourceQuery.data || resourceQuery.isError) {
|
||||
return (
|
||||
<div className="my-10 sm:my-16 md:my-28">
|
||||
<ErrorNotice
|
||||
icon
|
||||
header="Unable to pull available resources. Please try again."
|
||||
body="If this issue persists, please contact a site administrator"
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
const totalPages = Math.ceil(resourceQuery.data.count / queryData.perPage);
|
||||
const ConditionalTable = (data: {
|
||||
count: number;
|
||||
resources: AuditoryResource[];
|
||||
}) => {
|
||||
const totalPages = Math.ceil(data.count / queryData.perPage);
|
||||
|
||||
return (
|
||||
<ResourceTable
|
||||
resourcesPerPage={queryData.perPage}
|
||||
resources={resourceQuery.data.resources}
|
||||
resources={data.resources}
|
||||
totalPages={totalPages}
|
||||
query={router.query}
|
||||
currentPage={currentPage}
|
||||
@ -92,7 +79,8 @@ const Resources = () => {
|
||||
</Link>
|
||||
</section>
|
||||
</div>
|
||||
<ConditionalTable />
|
||||
|
||||
<QueryWaitWrapper query={resourceQuery} Render={ConditionalTable} />
|
||||
</div>
|
||||
</HeaderFooterLayout>
|
||||
);
|
||||
|
Loading…
x
Reference in New Issue
Block a user