Why use and When to use NextJS

Working on modern Javascript framework is amazing but there are a couple problems related to rendering all the content on the client-side like:

1- The page takes longer to fully load because all the JS must load, and your application needs to run to determine what to show on the page.

2- Search engines are getting better at running and indexing JavaScript apps, but it’s much better if we can send them content instead of letting them figure it out.

The solution to both of those problems is server rendering. and that is using a React Framework called NextJS. It provides a common structure that allows you to easily build a frontend React application, and transparently handles server-side rendering for you.

Main features provided by Next.js:

  • Next.js reloads the page when it detects any change saved to disk.
  • Automatic Routing –  put in the pages folder, and you don’t need any configuration
  • You can render React components on the server side, before sending the HTML to the client.
  • Instead of generating one single JavaScript file containing all the app code, the app is broken up automatically by Next.js in several different resources.Loading a page only loads the JavaScript necessary for that particular page.
  • The Link component, used to link together different pages, supports a prefetch prop which automatically prefetches page resources (including code missing due to code splitting) in the background.
  • You can import JavaScript modules and React Components dynamically.
  • Using the next export command,to export a fully static site from your app.
  • TypeScript support

Installing NextJS

1- Using create-next-app. Make sure that you have the latest version of Node.

npx create-next-app

2.then you can immediately run the sample app by running npm run dev And here’s the result on http://localhost:3000:

Adding a new page

For example if we wanted to add an About Page, create a new file under pages called about.js then add the code below

const About = () => (
    <div>
        <h1>About</h1>
        </div>
)
export default About

then visit the page http://localhost:3200/about

You can create a pages/about/company page, and that page will show up on the URL http://localhost:3000/about/company.

Dynamic content with the router

A blog is a great use case for this, For example a post titled “Hello World” might have the URL /blog/hello-world. We create a dynamic URL by creating a dynamic page with the [] syntax. So for the blog, we add a pages/blog/[id].js file. This file will handle all the dynamic URLs under the /blog/ route, like the ones we mentioned above.

  • We import it from next/router
  • and once we have useRouter, we instantiate the router object using:
const router = useRouter()
  • Once we have this router object, we can extract information from it. In particular we can get the dynamic part of the URL in the [id].js file by accessing router.query.id. The dynamic part can also just be a portion of the URL, like post-[id].js.
  • So lets create a file – pages/blog/[id].js and add the code
import { useRouter } from 'next/router' 
export default () => {   
const router = useRouter()   
return (     
<>       
<h1>Blog post</h1>       
<p>Post id: {router.query.id}</p>     
</>   
) 
}

Now if you go to http://localhost:3200/blog/post you can see this

We can use this id parameter to gather the post from a list of posts. From a database, for example. To keep things simple we’ll add a posts.json file in the project root folder.

Update the code to this:

import { useRouter } from 'next/router'
import posts from '../../posts.json'

export default () => {
  const router = useRouter()

  const post = posts[router.query.id]
  if (!post) return <p></p>

  return (
    <>
      <h1>{post.title}</h1>
      <p>{post.content}</p>
    </>
  )
}
Then it will display the content from the json file

Then we can add a blog page as well by adding a blog file and the code below:

import Link from 'next/link'
import posts from '../posts.json'
const Blog = () => (
    <div>
        <h1>Blog</h1>
        <ul>
      {Object.entries(posts).map((value, index) => {
        return (
          <li key={index}>
            <Link href='/blog/[id]' as={'/blog/' + value[0]}>
              <a>{value[1].title}</a>
            </Link>
          </li>
        )
      })}
    </ul>
    </div>
)

export default Blog

It will look like this

More next/router package

You can access the Next.js Router directly, provided in the next/router package, and call its push() method.

now we can use it’s methods:

push() allows us to programmatically trigger a URL change

router.push('/login')

prefetch() allows us to programmatically prefetch a URL, useful when we don’t have a Link tag which automatically handles prefetching for us

router.prefetch('/login') 

Full Code will look like:

import { useRouter } from 'next/router'
export default () => {
    const router = useRouter()
    useEffect(() => {
      router.prefetch('/login')
    })
  }

How do we make SSR work for dynamic routes

We must provide the component with props, using a special function called getInitialProps() which is attached to the component.

Now we are going to rewrite the post to:

import posts from '../../posts.json'
const Post = props => {
  return (
    <div>
      <h1>{props.post.title}</h1>
      <p>{props.post.content}</p>
    </div>
  )
}

Post.getInitialProps = ({ query }) => {
  return {
    post: posts[query.id]
  }
}
export default Post

The getInitialProps function will be executed on the server side, but also on the client side, when we navigate to a new page using the Link component as we did.

It’s important to note that getInitialProps gets, in the context object it receives, in addition to the query object these other properties:

  • pathname: the path section of URL
  • asPath – String of the actual path (including the query) shows in the browser

CSS

Next.js comes with styled-jsx built-in, because that’s a library built by the same people working on Next.js.

To add CSS to a React component in Next.js we insert it inside a snippet in the JSX, which start with

<style jsx>{`

and ends with

`}</style>

Inside this blocks we write plain CSS. Example:

import Link from 'next/link'

const Index = () => (
  <div>
    <h1>Home page</h1>
    <style jsx>{`
      h1 {
        font-size: 3rem;
      }
    `}</style>
    <Link href='/about'>
      <a>About Us</a>
    </Link>
  </div>
)

export default Index

Adding a wrapper component

All the pages on your site look more or less the same. There’s a chrome window, a common base layer, and you just want to change what’s inside. To do this:

create a components/Layout.js component:

export default Page => {
    return () => (
      <div>
        <nav>
          <ul>...</ul>
        </nav>
        <main>
          <Page />
        </main>
      </div>
    )
  }

And now you can update the index page to this

import Link from 'next/link'
import withLayout from '../pages/components/layout'

const Index = () => (
  <div>
    <h1>Home page</h1>
    <style jsx>{`
      h1 {
        font-size: 3rem;
      }
    `}</style>
    <Link href='/about'>
      <a>About Us</a>
    </Link>
  </div>
)


export default withLayout(Index)

To avoid unnecessarily complicating our codebase, the alternative approach is to use props:

In Layout.js it will be:

export default props => (
    <div>
      <nav>
        <ul>....</ul>
      </nav>
      <main>
        {props.content}
      </main>
    </div>
  )

and the pages we will code it like this:

import Layout from '../components/Layout.js'
const Page = () => (   
<Layout content={(     <p>Here's a page!</p>   )} /> 
)

That’s it for now, stay tune for the Part 2 of this post. and Enjoy coding NextJS!

One thought on “Why use and When to use NextJS

Add yours

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Website Powered by WordPress.com.

Up ↑

<span>%d</span> bloggers like this: