1

When page is refreshed query is lost, disappears from react-query-devtools.

Before Next.js, I was using a react and react-router where I would pull a parameter from the router like this:

const { id } = useParams();

It worked then. With the help of the, Next.js Routing documentation I have replaced useParams with:

import { usePZDetailData } from "../../hooks/usePZData";
import { useRouter } from "next/router";
const PZDetail = () => {
  const router = useRouter();
  const { id } = router.query;
  const { } = usePZDetailData(id);

  return <></>;
};

export default PZDetail;

Does not work on refresh. I found a similar topic, but manually using 'refetch' from react-query in useEffects doesn't seem like a good solution. How to do it then?

Edit

Referring to the comment, I am enclosing the rest of the code, the react-query hook. Together with the one already placed above, it forms a whole.

const fetchPZDetailData = (id) => {
  return axiosInstance.get(`documents/pzs/${id}`);
};

export const usePZDetailData = (id) => {
  return useQuery(["pzs", id], () => fetchPZDetailData(id), {});
};

Edit 2

I attach PZList page code with <Link> implementation

import Link from "next/link";
import React from "react";
import TableModel from "../../components/TableModel";
import { usePZSData } from "../../hooks/usePZData";
import { createColumnHelper } from "@tanstack/react-table";

type PZProps = {
  id: number;
  title: string;
  entry_into_storage_date: string;
};

const index = () => {
  const { data: PZS, isLoading } = usePZSData();
  const columnHelper = createColumnHelper<PZProps>();
  const columns = [
    columnHelper.accessor("title", {
      cell: (info) => (
        <span>
          <Link
            href={`/pzs/${info.row.original.id}`}
          >{`Dokument ${info.row.original.id}`}</Link>
        </span>
      ),
      header: "Tytuł",
    }),
    columnHelper.accessor("entry_into_storage_date", {
      header: "Data wprowadzenia na stan ",
    }),
  ];
  return (
    <div>
      {isLoading ? (
        "loading "
      ) : (
        <TableModel data={PZS?.data} columns={columns} />
      )}
    </div>
  );
};

export default index;
juliomalves
  • 42,130
  • 20
  • 150
  • 146
skelaw
  • 199
  • 4
  • 16
  • Is the issue that `id` isn't working, or is something in that `usePZDetailData` hook not working as expected? *What* is undefined? Please clarify the issue and please include all relevant code you are working with and have an issue using as part of your [mcve]. – Drew Reese Sep 11 '22 at 19:08
  • I have attached more code. Hmm.. The hook works fine when navigating to the details page via . I think there is something wrong with useRouter() implementation or is it the nature of NextJs? – skelaw Sep 11 '22 at 19:27
  • Can you share how you link to this page/component, and then also what exactly you are doing to produce the issue? – Drew Reese Sep 11 '22 at 19:29
  • I've included code with the implementation. Extra info: When I click on I am redirected to the PZDetail page, in ReactQueryDevtool I see a query, the data is rendered. After refreshing the page, the query from ReactQueryDevtool disappears, in the console it pops an error - inalid query. Django server gets invalid query and then gets a second valid query. – skelaw Sep 11 '22 at 19:40
  • 1
    I think that related post you found is probably what you are looking for with checking the `router.isReady` value. – Drew Reese Sep 11 '22 at 19:46

1 Answers1

4

What you're experiencing is due to the Next.js' Automatic Static Optimization.

If getServerSideProps or getInitialProps is present in a page, Next.js will switch to render the page on-demand, per-request (meaning Server-Side Rendering).

If the above is not the case, Next.js will statically optimize your page automatically by prerendering the page to static HTML.

During prerendering, the router's query object will be empty since we do not have query information to provide during this phase. After hydration, Next.js will trigger an update to your application to provide the route parameters in the query object.

Since your page doesn't have getServerSideProps or getInitialProps, Next.js statically optimizes it automatically by prerendering it to static HTML. During this process the query string is an empty object, meaning in the first render router.query.id will be undefined. The query string value is only updated after hydration, triggering another render.


In your case, you can work around this by disabling the query if id is undefined. You can do so by passing the enabled option to the useQuery call.

export const usePZDetailData = (id) => {
    return useQuery(["pzs", id], () => fetchPZDetailData(id), {
        enabled: id
    });
};

This will prevent making the request to the API if id is not defined during first render, and will make the request once its value is known after hydration.

juliomalves
  • 42,130
  • 20
  • 150
  • 146