Abhi
Abhi

Reputation: 1574

_app.getInitialProps is not called on every request

I am setting the theme based on the hostname. Everything works in dev mode, but I just ran npm run build and I see that getInitialProps gets called during build time. I cannot find any information on when _app's getInitialProps gets called.

I built the whole app thinking _app's getInitialProps gets called on every request. Does getInitialProps not get called from every request (initial page load and route changes)?

This is _app.tsx:

MyApp.getInitialProps = async (appContext: AppContext) => {
  
  const selectedBusinessWhitelabelKey = getWhitelabelKeyFromHostname(appContext.ctx.req?.headers.host || '');
  
  const selectedBusinessWhitelabelValues = whitelabel[selectedBusinessWhitelabelKey];
  return {
    ...appProps,
    selectedBusinessWhitelabelValues,
    themeObj: allThemes[selectedBusinessWhitelabelKey],
  };
};

The component:

function MyApp(props: AppProps & { emotionCache: EmotionCache; [key: string]: any }) {
  const { Component, emotionCache = clientSideEmotionCache, pageProps, themeObj, selectedBusinessWhitelabelValues } = props;
  const [theme] = useState(createTheme(themeObj));

  return (
    <CacheProvider value={emotionCache}>
      <ThemeProvider theme={theme}>
        <CssBaseline />
        <Layout selectedBusinessWhitelabelValues={selectedBusinessWhitelabelValues}>
          <Component {...pageProps} selectedBusinessWhitelabelValues={selectedBusinessWhitelabelValues} />
        </Layout>
      </ThemeProvider>
    </CacheProvider>
  );
}

If this is not the right way to set theme based on the hostname (the request domain), what else can I do?

Upvotes: 1

Views: 1766

Answers (1)

juliomalves
juliomalves

Reputation: 50398

The behaviour of getInitialProps in _app will vary based on the data fetching methods used in your pages:

  • For pages that use getStaticProps, the _app's getInitialProps function only gets called at build time.
  • For pages that use getServerSideProps, the _app's getInitialProps function gets called on every request and will always run on the server.
  • For pages that either use getInitialProps or do not have any data fetching method, the _app's getInitialProps function gets called on every request. For the initial page load getInitialProps will run on the server. For subsequents page navigations (using next/link or next/router) getInitialProps will then run on the client.

In your case, you're most likely experiencing the first scenario. If you want getInitialProps to run on every request, you either need to not use any data fetching method or use getServerSideProps in your pages.

Note that in development mode getInitialProps and getStaticProps get called on every page load, hence why you were only experiencing it in production mode.

Upvotes: 3

Related Questions