简体   繁体   English

如何在 Next.js 中使用 useEffect 调用 getServerSideprops

[英]How to call getServerSideprops with useEffect in Next.js

I am building a project using next.js but I have an issue that getServerSideProps is called 6 times when the page is rendered.我正在使用 next.js 构建一个项目,但我有一个问题,即在呈现页面时调用了 6 次 getServerSideProps。

Here is the code at the top in pages.这是页面顶部的代码。

const NewFindstay: React.FC<INewFindstayProps> = ({ findstayList }) => {
  const [isMap, setIsMap] = useState(false);
  return (
    <div id="contents">
      <FindstayFilter setIsMap={setIsMap} isMap={isMap} />
      <FindstayList findstayList={findstayList} isMap={isMap} />
    </div>
  );
};

export async function getServerSideProps({ query, req }) {
  let findstayList = null;
  try {
    findstayList = await getPlaceListAsync(
      { ...query },
      req.headers.cookie ? req.headers.cookie : null
    );
  } catch (e) {
    findstayList = null;
  }
  return {
    props: {
      findstayList,
      query,
    },
  };
}

export default NewFindstay;

Seems this is caused by components that imported inside of FindstayFilter.似乎这是由在 FindstayFilter 中导入的组件引起的。 (let's say components A, B, C, D, E, F) (假设组件 A、B、C、D、E、F)

Each components of A, B, C, D, E, F has useEffect hook for setState. A、B、C、D、E、F的每个组件都有setState的useEffect hook。

// A
 useEffect(() => {
    if (router.query.city) {
      setSelectedCity(router.query.city);
    };
  }, [router.query.city]);

// B
  useEffect(() => {
    setDateRange({
      startDate: check_in ? moment(check_in) : null,
      endDate: check_out ? moment(check_out) : null
    })
  }, [router.query.check_in, router.query.check_out]);
// C
  useEffect(() => {
    const queryPrice = {
      min: price_min ? (parseInt(price_min as string, 10) / 10000) : 0,
      max: price_max ? (parseInt(price_max as string, 10) / 10000) : 100
    }
    setRangePrice(queryPrice);
  }, [router.query.price_min, router.query.price_max]);

// D, E, F use same pattern as well.

In order words, when FindstayFilter component renders, useEffect hook inside A, B, C, D, E, F rerender the component total 6 times which triggers calling getServerSideProps 6 times as well.换句话说,当 FindstayFilter 组件渲染时,A、B、C、D、E、F 内部的 useEffect hook 总共重新渲染组件 6 次,触发调用 getServerSideProps 6 次。

How can I minimize calling getServerSideProps?如何最小化调用 getServerSideProps? should I use useEffect hook only inside of FindstayFilter component and crammed many setstate code into the hook?我应该只在 FindstayFilter 组件内部使用 useEffect 钩子并将许多 setstate 代码塞进钩子吗?

getServerSideProps is only called when the page first loads because it will call the nodejs server of nextjs. getServerSideProps仅在页面首次加载时调用,因为它会调用 nextjs 的 nodejs 服务器。 That will be always the case no mater what, unless you do some reloading/refreshing the page.无论如何,情况总是如此,除非您重新加载/刷新页面。 https://nextjs.org/docs/basic-features/data-fetching#getserversideprops-server-side-rendering https://nextjs.org/docs/basic-features/data-fetching#getserversideprops-server-side-rendering

I have found what was wrong.我发现出了什么问题。

I put useEffect hook with dependency array state inside in every component so that whenever states changes, router.push works.我将 useEffect 钩子和依赖数组 state 放在每个组件中,这样只要状态发生变化, router.push 就可以工作。

  const pushRouter = (renderQuery) => {
    return (
      router.push({
        pathname: "/findstay",
        query: {
          ...router.query,
          ...renderQuery,
          page: 1,
          per: 10
        }
      })
    );
  };

  useEffect(() => {
    const queryCnt = {
      adultCnt: adult_cnt ? parseInt(adult_cnt as string, 10) : 0,
      childCnt: child_cnt ? parseInt(child_cnt as string, 10) : 0,
      babyCnt: baby_cnt ? parseInt(baby_cnt as string, 10) : 0
    };
    pushRouter(queryCnt)
  }, [adult_cnt, child_cnt, baby_cnt]);

However router.push works as ssr in my code(it is supposed to work as csr) which means when FindstayFilter renders, pushRouter function in children components A, B, C, D, E, F also works and this leads to getServerSideProps renders 6 times.但是 router.push 在我的代码中作为 ssr 工作(它应该作为 csr 工作),这意味着当FindstayFilter渲染时,子组件 A、B、C、D、E、F 中的 pushRouter function 也可以渲染,这会导致 getServerSideProps 渲染次。

Now I have to find a reason why router.push works ssr https://github.com/vercel/next.js/issues/9586现在我必须找到 router.push 工作的原因 ssr https://github.com/vercel/next.js/issues/9586

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM