[WIP] Migrate /your-outfits to Next.js routing

This one was pretty boring! I was relieved to see the pagination changes seem to just work though 😅
This commit is contained in:
Emi Matchu 2022-09-14 20:19:14 -07:00
parent 02af99dded
commit 1dbc142f4f
4 changed files with 59 additions and 43 deletions

5
pages/your-outfits.tsx Normal file
View file

@ -0,0 +1,5 @@
import UserOutfitsPage from "../src/app/UserOutfitsPage";
export default function UserOutfitsPageWrapper() {
return <UserOutfitsPage />;
}

View file

@ -24,7 +24,6 @@ const UserItemListsIndexPage = loadable(() =>
import("./UserItemListsIndexPage") import("./UserItemListsIndexPage")
); );
const UserItemListPage = loadable(() => import("./UserItemListPage")); const UserItemListPage = loadable(() => import("./UserItemListPage"));
const UserOutfitsPage = loadable(() => import("./UserOutfitsPage"));
const WardrobePage = loadable(() => import("./WardrobePage"), { const WardrobePage = loadable(() => import("./WardrobePage"), {
fallback: <WardrobePageLayout />, fallback: <WardrobePageLayout />,
}); });
@ -90,11 +89,6 @@ function App() {
<UserItemListsIndexPage /> <UserItemListsIndexPage />
</PageLayout> </PageLayout>
</Route> </Route>
<Route path="/your-outfits">
<PageLayout>
<UserOutfitsPage />
</PageLayout>
</Route>
<Route path="/"> <Route path="/">
<PageLayout hideHomeLink> <PageLayout hideHomeLink>
<HomePage /> <HomePage />

View file

@ -3,7 +3,8 @@ import { Box, Center, Flex, Wrap, WrapItem } from "@chakra-ui/react";
import { ClassNames } from "@emotion/react"; import { ClassNames } from "@emotion/react";
import gql from "graphql-tag"; import gql from "graphql-tag";
import { useQuery } from "@apollo/client"; import { useQuery } from "@apollo/client";
import { Link, useLocation } from "react-router-dom"; import Link from "next/link";
import { useRouter } from "next/router";
import { Heading1, MajorErrorMessage, useCommonStyles } from "./util"; import { Heading1, MajorErrorMessage, useCommonStyles } from "./util";
import HangerSpinner from "./components/HangerSpinner"; import HangerSpinner from "./components/HangerSpinner";
@ -55,8 +56,8 @@ const PER_PAGE = 20;
function UserOutfitsPageContent() { function UserOutfitsPageContent() {
const { isLoggedIn, isLoading: userLoading } = useCurrentUser(); const { isLoggedIn, isLoading: userLoading } = useCurrentUser();
const { search } = useLocation(); const { query } = useRouter();
const offset = parseInt(new URLSearchParams(search).get("offset")) || 0; const offset = parseInt(query.offset) || 0;
const { loading: queryLoading, error, data } = useQuery( const { loading: queryLoading, error, data } = useQuery(
USER_OUTFITS_PAGE_QUERY, USER_OUTFITS_PAGE_QUERY,
@ -171,9 +172,9 @@ function OutfitCard({ outfit }) {
); );
return ( return (
<Link href={`/outfits/${outfit.id}`} passHref>
<Box <Box
as={Link} as="a"
to={`/outfits/${outfit.id}`}
display="block" display="block"
transition="all 0.2s" transition="all 0.2s"
_hover={{ transform: `scale(1.05)` }} _hover={{ transform: `scale(1.05)` }}
@ -185,6 +186,7 @@ function OutfitCard({ outfit }) {
> >
<OutfitCardLayout image={image} caption={outfit.name} /> <OutfitCardLayout image={image} caption={outfit.name} />
</Box> </Box>
</Link>
); );
} }

View file

@ -1,6 +1,7 @@
import React from "react"; import React from "react";
import { Box, Button, Flex, Select } from "@chakra-ui/react"; import { Box, Button, Flex, Select } from "@chakra-ui/react";
import { Link, useHistory, useLocation } from "react-router-dom"; import Link from "next/link";
import { useRouter } from "next/router";
function PaginationToolbar({ function PaginationToolbar({
isLoading, isLoading,
@ -8,22 +9,20 @@ function PaginationToolbar({
numPerPage = 30, numPerPage = 30,
...props ...props
}) { }) {
const { search } = useLocation(); const { query, push: pushHistory } = useRouter();
const history = useHistory();
const currentOffset = const currentOffset = parseInt(query.offset) || 0;
parseInt(new URLSearchParams(search).get("offset")) || 0;
const currentPageIndex = Math.floor(currentOffset / numPerPage); const currentPageIndex = Math.floor(currentOffset / numPerPage);
const currentPageNumber = currentPageIndex + 1; const currentPageNumber = currentPageIndex + 1;
const numTotalPages = totalCount ? Math.ceil(totalCount / numPerPage) : null; const numTotalPages = totalCount ? Math.ceil(totalCount / numPerPage) : null;
const prevPageSearchParams = new URLSearchParams(search); const prevPageSearchParams = new URLSearchParams(query);
const prevPageOffset = currentOffset - numPerPage; const prevPageOffset = currentOffset - numPerPage;
prevPageSearchParams.set("offset", prevPageOffset); prevPageSearchParams.set("offset", prevPageOffset);
const prevPageUrl = "?" + prevPageSearchParams.toString(); const prevPageUrl = "?" + prevPageSearchParams.toString();
const nextPageSearchParams = new URLSearchParams(search); const nextPageSearchParams = new URLSearchParams(query);
const nextPageOffset = currentOffset + numPerPage; const nextPageOffset = currentOffset + numPerPage;
nextPageSearchParams.set("offset", nextPageOffset); nextPageSearchParams.set("offset", nextPageOffset);
const nextPageUrl = "?" + nextPageSearchParams.toString(); const nextPageUrl = "?" + nextPageSearchParams.toString();
@ -42,23 +41,25 @@ function PaginationToolbar({
const newPageIndex = newPageNumber - 1; const newPageIndex = newPageNumber - 1;
const newPageOffset = newPageIndex * numPerPage; const newPageOffset = newPageIndex * numPerPage;
const newPageSearchParams = new URLSearchParams(search); const newPageSearchParams = new URLSearchParams(query);
newPageSearchParams.set("offset", newPageOffset); newPageSearchParams.set("offset", newPageOffset);
history.push({ search: newPageSearchParams.toString() }); pushHistory("?" + newPageSearchParams.toString());
}, },
[search, history, numPerPage] [query, pushHistory, numPerPage]
); );
return ( return (
<Flex align="center" justify="space-between" {...props}> <Flex align="center" justify="space-between" {...props}>
<Button <LinkOrButton
as={prevPageIsDisabled ? "button" : Link} href={prevPageIsDisabled ? undefined : prevPageUrl}
to={prevPageIsDisabled ? undefined : prevPageUrl} _disabled={{
_disabled={{ cursor: isLoading ? "wait" : "not-allowed", opacity: 0.4 }} cursor: isLoading ? "wait" : "not-allowed",
opacity: 0.4,
}}
isDisabled={prevPageIsDisabled} isDisabled={prevPageIsDisabled}
> >
Prev Prev
</Button> </LinkOrButton>
{numTotalPages && ( {numTotalPages && (
<Flex align="center"> <Flex align="center">
<Box flex="0 0 auto">Page</Box> <Box flex="0 0 auto">Page</Box>
@ -73,18 +74,32 @@ function PaginationToolbar({
<Box flex="0 0 auto">of {numTotalPages}</Box> <Box flex="0 0 auto">of {numTotalPages}</Box>
</Flex> </Flex>
)} )}
<Button <LinkOrButton
as={nextPageIsDisabled ? "button" : Link} href={nextPageIsDisabled ? undefined : nextPageUrl}
to={nextPageIsDisabled ? undefined : nextPageUrl} _disabled={{
_disabled={{ cursor: isLoading ? "wait" : "not-allowed", opacity: 0.4 }} cursor: isLoading ? "wait" : "not-allowed",
opacity: 0.4,
}}
isDisabled={nextPageIsDisabled} isDisabled={nextPageIsDisabled}
> >
Next Next
</Button> </LinkOrButton>
</Flex> </Flex>
); );
} }
function LinkOrButton({ href, ...props }) {
if (href != null) {
return (
<Link href={href} passHref>
<Button as="a" {...props} />
</Link>
);
} else {
return <Button {...props} />;
}
}
function PageNumberSelect({ function PageNumberSelect({
currentPageNumber, currentPageNumber,
numTotalPages, numTotalPages,