Tim Hysniu
Tim Hysniu

Reputation: 1540

Linking to page causes re-render of entire page in NextJS

I have static pages and some dynamic pages with following page components:

pages/home.js
pages/about.js
pages/search/[term].js

To link the pages I am using next/link. Going from static to static pages performs pretty well. However, when I navigate to pages/search/[term].js I can see that the entire page re-renders. This is pretty bad user experience if you are expecting the app to behave like an SPA. My assumption was the nextjs will render pages on server side and on all subsequent requests it will diff the components rendered with what needs to re-render and then re-render only updated components. If this was the case though, the Nav component would not re-render.

Is it possible to only have changing components re-render? I might be doing something wrong. I have tried making sure that I'm not unnecessarily changing props which may result in re-render but no luck so far. On Dev Tools I see 404 requests on static files which makes sense because this is a dynamic page: http://localhost:3000/_next/static/development/pages/search/hello.js net::ERR_ABORTED 404 (Not Found)

My layout looks like this:

import Head from 'next/head';
import Navbar from './Navbar';

const Layout = (props) => (
  <div>
    <Head>
      <title>Some title</title>
    </Head>
    <Navbar  />
    {props.children}
  </div>
);

export default Layout;

...and a page looks something like this:

import Layout from '../components/Layout';

const About = (props) => (
  <Layout>
    <main className="main">
      <div className="container">
        <h1>About</h1>
        <Link href="/">Go home</Link>
      </div>
    </main>

  </Layout>
);


export default About;

and [term].js:


class Search extends React.Component {
  static async getInitialProps({ query, req }) { 
    return { query };
  }

  render() {
     const { query } = this.props;
     return (<p>{JSON.stringify(query)}</p>);
  }
}

export default Search;

Upvotes: 3

Views: 3137

Answers (1)

Tim Hysniu
Tim Hysniu

Reputation: 1540

This was an oversight with dynamic link handling. NextJS was treating the link as static. To handle the dynamic links I should have added the as attribute to Link as per documentation:

<Link href="/search/[term]" as={`search/${term}`}>...</Link>

where the term is actual term value coming from props. This fixed my problem.

Upvotes: 2

Related Questions