Search code examples
reactjsi18nextreact-i18next

{ useTranslation } from "react-i18next" library outputs error


I have the following code:

import React, { Suspense } from "react";
import { useTranslation } from "react-i18next";
import "../i18n";
const Loader = () => {
  return (
    <div>
      <h3>loading...</h3>
    </div>
  );
};
export default props => {
  const { t } = useTranslation(); //the problem is in this line

  return (
    <Suspense fallback={<Loader />}>
        <h1>{t("testTitle")}</h1>
    </Suspense>
  );
};

But it doesn't work. Instead, a red screen shows up with the following text: A React component suspended while rendering, but no fallback UI was specified. Add a component higher in the tree to provide a loading indicator or placeholder to display

At the beginning, I thought the problem came from <Suspense fallback={<Loader/>}> line, but after a couple of tries, I've fond out that it's actually coming for the useTranslation() line.

How can I fix this?


Solution

  • I've found what's causing the problem: although the useTranslation() line is inside the default component, it's out of the <Suspense fallback={<Loader />}> scope. So the solution is to NOT export that component. Instead, you have to assign it into a variable, and then create a new component which wraps it:

    import React, { Suspense } from "react";
    import { useTranslation } from "react-i18next";
    import "../i18n";
    const Loader = () => {
      return (
        <div>
          <h3>loading...</h3>
        </div>
      );
    };
    const FirstComponent = props => { //You assign it into a varible instead of exporting directly
    
      const { t } = useTranslation(); 
    
      return (
        <Suspense fallback={<Loader />}>
            <h1>{t("testTitle")}</h1>
        </Suspense>
      );
    };
    
    export default props => { //This is the component that you have to export instead
    
      return (
        <Suspense fallback={<Loader />}>
            <FirstComponent/>
        </Suspense>
      );
    };