Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Error: pages/404 can not have getInitialProps/getServerSideProps #677

Closed
Danetag opened this issue Apr 3, 2020 · 32 comments
Closed

Error: pages/404 can not have getInitialProps/getServerSideProps #677

Danetag opened this issue Apr 3, 2020 · 32 comments

Comments

@Danetag
Copy link

Danetag commented Apr 3, 2020

Describe the bug

After setting up next-i18next, I have the following error in the terminal on every page (probably because it's looking for an not existing favicon.ico by default).

Error: `pages/404` can not have getInitialProps/getServerSideProps, https://err.sh/zeit/next.js/404-get-initial-props

But my 404 page is really simple, no getInitialProps/getServerSideProps

export default () => <h1>This is the 404 page</h1>

Note: i'm trying the setup the project for a potential future translation. Therefore, next-i18next provides a clean way for developers to use the system as string dictionary for UI texts, which later on could be translated.

Obviously, if I go to /404, I see the error in browser.

Thank you!

Occurs in next-i18next version

From the package-lock.json and other info

  • next-i18next: 4.2.1
  • i18next: 19.3.4
  • node JS: 13.9.0
  • npm: 6.13.7

Steps to reproduce

File structure

└── public
    └── static
        └── locales
            ├── en
               └── common.json
               └── homepage.json
└── src
     └── pages
     └── components

In i18n.js
Note: I needed to add those properties in the config to be able to make t('key) working

lng: 'en',
fallbackLng: 'en',
languages: ['en', 'not-existing-yet'],

More specifically lng: 'en', the fallbackLng is for later if we do add more languages, and languages to be able to access i18n.languages (otherwise it wasn't working)

const NextI18Next = require('next-i18next').default

const NextI18NextInstance = new NextI18Next({
  defaultLanguage: 'en',
  lng: 'en',
  fallbackLng: 'en',
  languages: ['en', 'not-existing-yet'],
  otherLanguages: ['not-existing-yet'],
})

module.exports = NextI18NextInstance;

In _app.js

import React from "react";
import App from "next/app";

// i18n
import { appWithTranslation } from '~/i18n'

class MyApp extends App {
  render() {
    const { Component, pageProps } = this.props;

    return (
      <>
            <Head>
              <title>NextJS Advanced Routing</title>
            </Head>
            
            <Component {...pageProps} />
      </>
    );
  }
}

export default appWithTranslation(MyApp);

In index.js (homepage)

import { withTranslation } from '~/i18n'

const Index = ({ data, t, ...props }) => {
   return (
     <h1>{ t('homepage:title') }</h1>
   )
}

Index.getInitialProps = async ({ query }) => {
  // get some data
  const data = await getData();
  return { data, namespacesRequired: ['common', 'homepage'], }
}

export default withTranslation('homepage')(Index)

Expected behaviour

404 should be working without triggering an error

Screenshots

OS (please complete the following information)

  • Device:MBP 2019 15"
  • Browser: Chrome 80.0.3987.149

Additional context

@felixmosh
Copy link
Contributor

Actually this Next's requirement is absurd, cause if you have translations you must translate your custom 404 as well.

@isaachinman
Copy link
Contributor

Yeah, @Danetag this is probably an issue to raise with the NextJs team. There's not much that can be done on the next-i18next side of things - we have to get translations somehow.

@RobinLebhar
Copy link

RobinLebhar commented Jun 13, 2020

Hello, you are right we should be able to translate the 404 page as well ! (great job on this repo btw)

Is it possible to disable the warning though ? Because all my other pages are correctly setup and I would like to avoid to be spamed by the warning when navigating to the 404 page.

Thank you !

@isaachinman
Copy link
Contributor

Just to follow up: I don't think it's right to disable the warning. I think the correct thing to do is translate our 404 pages.

I can speak to the NextJs team about this.

@ghost
Copy link

ghost commented Jul 21, 2020

Any updates?

@Dynkin
Copy link

Dynkin commented Aug 3, 2020

Yeah. I'm facing the same issue now. I like to keep my console clean. But in this particular situation I get or warning from Next.js You should have custom 404 page because it's good to optimize its as static content either warning from next-18next You have not declared a namespacesRequired array on your page-level component: Custom404.

Frustrating 😞

@anthonyrenard
Copy link

@Dynkin, you can add your custom 404 page without the getInitialProps. Actually i'm running with this solution. it's not the best solution but it's working.

import PropTypes from 'prop-types';
import { withTranslation } from '../i18n';

function Custom404({ t }) {
  return (
    <div>
      <h1>{t('title-message')}</h1>
    </div>
  );
}

Custom404.propTypes = {
  t: PropTypes.func.isRequired,
};

export default withTranslation('404')(Custom404);

@geryit
Copy link

geryit commented Aug 25, 2020

@Dynkin, you can add your custom 404 page without the getInitialProps. Actually i'm running with this solution. it's not the best solution but it's working.

import PropTypes from 'prop-types';
import { withTranslation } from '../i18n';

function Custom404({ t }) {
  return (
    <div>
      <h1>{t('title-message')}</h1>
    </div>
  );
}

Custom404.propTypes = {
  t: PropTypes.func.isRequired,
};

export default withTranslation('404')(Custom404);

I still see the error @anthonyrenard

@Kerim-Willem
Copy link

@Dynkin, I'm also still seeing the error if I use your method!

@slava-lu
Copy link
Contributor

I tried default props instead of getInitialProps but it did not get the message away

@kefimochi
Copy link

Any updates on this? 👀

@isaachinman
Copy link
Contributor

I haven't heard any updates from the Vercel team. Not much to be done in user land.

@allan2
Copy link
Contributor

allan2 commented Sep 11, 2020

Feature request opened at vercel/next.js#17004

@mimimimichael
Copy link

New to next.js and currently fiddling around to solve the same problem.

I noticed, that if I don't have a 404.js page, it will fallback to the _error.js page to display the 404 Error and inside _error.js it is possible to use "getInitialProps".

I am using that for now as a workaround. It solves the translation problem, but it does cause another warning:

"You have added a custom /_error page without a custom /404 page. This prevents the 404 page from being auto statically optimized."

@apt-exploit
Copy link

The same problem is happening to me, it without getInitialProps but it doesn't work.

@morjanmihail
Copy link

morjanmihail commented Nov 23, 2020

Ok, so basically we're getting errors having and not having getInitialProps. Any workarounds for getting rid of those errors?

@CalebLovell
Copy link

Any updates for this? Seems crazy to not be able to translate 404s...

@isaachinman
Copy link
Contributor

@CalebLovell As next-i18next@beta supports other data-fetching methods, this should no longer be an issue. See #869.

@isaachinman
Copy link
Contributor

This is now possible with [email protected], by using getServerSideProps on your custom error page.

@kachar
Copy link

kachar commented May 5, 2021

I've stumbled upon this discussion but couldn't find the solution right away here, so I'm posting it for future reference:

This solution uses "next-i18next": "^8.2.0" with "next": "^10.2.0"

// pages/404.tsx
import { GetStaticProps } from 'next'
import NextErrorComponent from 'next/error'
import { useTranslation } from 'next-i18next'
import { serverSideTranslations } from 'next-i18next/serverSideTranslations'

export const getStaticProps: GetStaticProps = async ({ locale }) => {
  return {
    props: {
      ...(await serverSideTranslations(locale ?? 'en', ['common'])),
    },
  }
}

const NotFoundPage = () => {
  const { t } = useTranslation()
  return <NextErrorComponent statusCode={404} title={t('error.title')} />
}

export default NotFoundPage

@nicolasconnault
Copy link

I've stumbled upon this discussion but couldn't find the solution right away here, so I'm posting it for future reference:

Apparently this is supposed to work for the 500 page too, but it's not working for me :(

@lauriskuznecovs
Copy link

lauriskuznecovs commented May 21, 2021

Does not work for me either

"next": "^10.2.2",
"next-i18next": "^8.3.0",

In my case I am using this into custom error page inside getInitialProps

Getting this error in terminal:

error - ./node_modules/next-i18next/dist/commonjs/serverSideTranslations.js:48:0
Module not found: Can't resolve 'fs'

----- UPDATE
According to https://github.com/isaachinman/next-i18next#serversidetranslations serverSideTranslations works only with getStaticProps or getServerSideProps but in custom error page - "pages/_error.js" there are no support for those.

@vitagon
Copy link

vitagon commented Jun 16, 2021

I've stumbled upon this discussion but couldn't find the solution right away here, so I'm posting it for future reference:

This solution uses "next-i18next": "^8.2.0" with "next": "^10.2.0"

// pages/404.tsx
import { GetStaticProps } from 'next'
import NextErrorComponent from 'next/error'
import { useTranslation } from 'next-i18next'
import { serverSideTranslations } from 'next-i18next/serverSideTranslations'

export const getStaticProps: GetStaticProps = async ({ locale }) => {
  return {
    props: {
      ...(await serverSideTranslations(locale ?? 'en', ['common'])),
    },
  }
}

const NotFoundPage = () => {
  const { t } = useTranslation()
  return <NextErrorComponent statusCode={404} title={t('error.title')} />
}

export default NotFoundPage

I came from google. It works! Saved my time. Thank you. Hopefully we do not need getServerSideProps on 404 page.

@chrillo
Copy link

chrillo commented Oct 5, 2021

I spend an afternoon fiddling with this I managed to get the following to work

import { GetServerSideProps, NextPage } from 'next';
import { SSRConfig } from 'next-i18next';
import { serverSideTranslations } from 'next-i18next/serverSideTranslations';
import React, { useEffect, useState } from 'react';
import { useTranslation, withTranslation } from 'react-i18next';
import { Footer } from '../components/footer/footer';
import { Navigation } from '../components/navigation/navigation';
import { NotFoundHero } from '../components/not-found/notFoundHero';

export type NotFoundPageProps = SSRConfig & { locale: string };

const Page404Component: NextPage<NotFoundPageProps> = ({ locale }) => {
	const { t } = useTranslation();
	const [menus, setMenus] = useState([]);
	const loadMenus = async () => {
		const res = await fetch(`/api/menus?locale=${locale}`);
		const menus = await res.json();
		setMenus(menus);
	};
	useEffect(() => {
		loadMenus();
	}, []);
	return (
		<main>
			<Navigation menus={menus} slugs={{}} />

			<NotFoundHero
				title={t('notfound.title')}
				description={t('notfound.description')}
				imageDescription={t('notfound.imageDescription')}
			/>

			<Footer menus={menus} slugs={{}} />
		</main>
	);
};

export const getStaticProps: GetServerSideProps<NotFoundPageProps> = async ({
	locale,
	preview,
}) => {
	const translations = await serverSideTranslations(locale, ['common']);

	return {
		props: {
			locale,
			...translations,
		},
	};
};

const Translated404Page = withTranslation('translations')(Page404Component);

const Page404 = (props) => {
	return <Translated404Page {...props} useSuspense={false} />;
};

export default Page404;

the important part was to use withTranslation to get the translation context and to disable suspense as it is not yet supported. basically this allows a for a fully translated 404 page with client side data fetching for additional stuff like navigation etc.

@andrevenancio
Copy link

andrevenancio commented Nov 18, 2021

This works for me. On my specific case I need to import both footer and errors locale.

import { useTranslation } from 'next-i18next';
import { serverSideTranslations } from 'next-i18next/serverSideTranslations';

export default function Custom404() {
  const { t } = useTranslation('errors');

  return (
    <div>
      <h1>404</h1>
      <p>{t('404')}</p>
    </div>
  );
}

export async function getStaticProps(context: any) {
  let localisation = {};
  if (context.locale) {
    localisation = await serverSideTranslations(context.locale, ['errors', 'footer']);
  }

  return {
    props: {
      ...localisation,
    },
  };
}

@nataliagoskapracuj
Copy link

This works for me. On my specific case I need to import both footer and errors locale.

import { useTranslation } from 'next-i18next';
import { serverSideTranslations } from 'next-i18next/serverSideTranslations';

export default function Custom404() {
  const { t } = useTranslation('errors');

  return (
    <div>
      <h1>404</h1>
      <p>{t('404')}</p>
    </div>
  );
}

export async function getStaticProps(context: any) {
  let localisation = {};
  if (context.locale) {
    localisation = await serverSideTranslations(context.locale, ['errors', 'footer']);
  }

  return {
    props: {
      ...localisation,
    },
  };
}

On build I get an error

Error occurred prerendering page "/pl/404". Read more: https://nextjs.org/docs/messages/prerender-error
Error: Error serializing ._nextI18Next.userConfig.i18n.reloadOnPrerender returned from getStaticProps in "/404".
Reason: undefined cannot be serialized as JSON. Please use null or omit this value.c

@marcelobitorical
Copy link

Any updates on this? 👀

@martinharyanto
Copy link

martinharyanto commented Jun 27, 2023

Still having this issue using "next-i18next": "^13.2.2" and "next": "13.3.1"
I try to create pages/404.tsx

import Button from '@/components/ui/Button'
import { GetStaticProps, NextPage } from 'next'
import { serverSideTranslations } from 'next-i18next/serverSideTranslations'
import Image from 'next/image'

const Custom400Page: NextPage{}> = ({}) => {
  return (
    <div className='flex flex-col items-center justify-center'>
      <Image src='/images/500.svg' alt='500 Error Icon' width={200} height={135} />
      <h1 className=''>Internal System Error</h1>
      <span>Something went wrong at our end. Back to home to refresh your page.</span>
      <Button id='back-to-home' handleClick={() => {}} text='Home' />
    </div>
  )
}

export const getStaticProps: GetStaticProps = async ({ locale }) => {
  return {
    props: {
      ...(await serverSideTranslations(locale ?? 'en', ['common'])),
    },
  }
}

export default Custom400Page

upon building the app, it shows bunch of errors:

Error occurred prerendering page "/id/404". Read more: https://nextjs.org/docs/messages/prerender-error
Error occurred prerendering page "/en/404". Read more: https://nextjs.org/docs/messages/prerender-error

info  - Generating static pages (2/2)

> Export encountered errors on following paths:
        /404: /en/404
        /404: /id/404
error Command failed with exit code 1.

@HimanshuBari21
Copy link

HimanshuBari21 commented Feb 19, 2024

https://nextjs.org/docs/messages/404-get-initial-props - as per the docs by next.js - they says data fetching is not allowed in 404.js/.ts page and suggest to adopt to App Router incrementally. but its not feasible for me to do this.

I need to fetch data, because options in my menu are based on user login in status and user type. and menu is also there on 404 page.

@jamesryan-dev
Copy link

@HimanshuBari21 did you ever find a solution for this?

@HimanshuBari21
Copy link

No, We choose not to personalize menu on 404 page 😞

@pdparchitect
Copy link

You can create another route that provides the needed props and load them yourself with fetch directly from the _next route. It is a bit of a hack but it could work. That being said, it is shame that this is not possible and the only route is the buggy app router.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests