LoginSignup
19
5

More than 1 year has passed since last update.

【React】useEffectやuseState使用時に「Rendered more hooks than during the previous render」のエラーが発生

Posted at

概要

表題のエラーについて、Reactをやったことある人であれば、一度は見かけたことがある内容かもしれません。私はいまだに、このReactのエラー仕様をド忘れしてハマることがあるので、今回は備忘でメモ書きします。

どういう時に発生するのか

こちらのteratailの記事にある通り、「useXxx関数を条件やループに入れたり、手前でreturnしてしまったりするとこういうエラー」となります。NGパターンの詳細については、Rendered more hooks than during the previous render (React)の記事でも解説されています。

例えば以下のようなソースでは、useEffectの手前で条件式でreturnしてしまってるので、エラーになります。

import { useContext, useEffect } from "react";
import { useQuery } from "react-query";
import { SampleContext } from "../context/SampleProvider";
import { getSearchMaster } from "../service/api/SearchService";

export default function SampleComponent() {
  const { master, setMaster } = useContext(SampleContext);
  const { data, isError, isLoading } = useQuery("master", getSearchMaster);

  if (isLoading) {
    return (<>Loading・・・</>);
  }

  if (isError) {
    return (<>Error</>);
  }

  useEffect(() => {
    if (data) {
      setMaster(data);
    }
  }, [data]);

  return (<>成功</>);
}

対応

トップレベルにて、条件付きでuseXxxを呼び出したり、useXxxが呼ばれる前にreturnしないよう、修正すれば大丈夫です。
上記のサンプルソースについて、以下のように修正すればエラーは解消されます。

import { useContext, useEffect } from "react";
import { useQuery } from "react-query";
import { SampleContext } from "../context/SampleProvider";
import { getSearchMaster } from "../service/api/SearchService";

export default function SampleComponent() {
  const { master, setMaster } = useContext(SampleContext);
  const { data, isError, isLoading } = useQuery("master", getSearchMaster);

  useEffect(() => {
    if (data) {
      setMaster(data);
    }
  }, [data]);

  if (isLoading) {
    return (<>Loading・・・</>);
  }

  if (isError) {
    return (<>Error</>);
  }

  return (<>成功</>);
}
19
5
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
19
5