Let's talk about Next.js

Getting Started

v11 features

and

A Brief Recap of SSR

Work Flow of SPA & SSR

See Steven's Slide for more

Next.js as a SSR framework for React

  1. Built-in and intuitive Routing System

  2. Prerendering with SSG and SSR on per-page basis

  3. Automatic code splitting for faster page loads

  4. Client-side routing with optimized prefetching

  5. Support for Sass, PostCSS and any CSS-in-JS library

  6. Development environment with Fast Refresh support

  7. API routes to build API endpoints with Serverless Functions

Getting Started !

Page-based Routing System

/pages:one-to-one static router for your site

"/" → pages/index.js

"/about" → pages/about.js

"/post/my-example (/post/:id)" → pages/post/[id]/index.js

"/post/my-example/a-comment (/post/:id/:comment)" → pages/post/[id]/[comment].js

filename as the route name and nested like folder structure

Client-side Routing

1. Built-in Link tag

<a>:Fully Refetch

<Link> : Using JS to change root div

2. Prefetch in background

Notes: Link only do route within APP

3. Code Splitting

<Link href="/">
  <a>Back to home</a>
</Link>
  • Faster page loads
  • Isolate pages and prevent crash

Assets, Metadata, and CSS

  • Assets: /public
     
  • Metadata:next/head
     
  • CSS:Built-in Support for CSS modules, CSS-In-JS,and Sass
"/public/test.img" 👉  src="/test.img"

next/head

To modify each page's metadata

  • title, description
  • link, scripts         
  • Open Graph Tags

CSS Integration

  1. Global CSS in pages/_app.tsx
  2. CSS Modules with [name].module.css
  3. Built-in PostCss and Customizable Config (useful for Tailwind)
  4. Built-in SCSS Support with .sass/scss, .module.sass/scss

Prerendering

  1. Generates HTML for each page in advance     → Better Performance & SEO
  2. Keep the minimal JS code
     → Hydration

Static Generation and Server-Side Rendering

Choice on Per Page Basis

Static Generation

When To Use ?

getStaticProps

Pre-render the page ahead of a user's request.

Recommend for most pages.

export default function Home(props) { ... }

export async function getStaticProps() {
  // Get external data from the file system, API, DB, etc.
  const data = ...

  // The value of the `props` key will be
  //  passed to the `Home` component
  return {
    props: ...
  }
}
  1. Fetch data inside the app

  2. Fetch external data

  3. Directly query from DB
    (Server-side Rendering)

Server-side Rendering

When To Use ?

getServerSideProps

Pre-render a page data whose be fetched at request time

TTFB is slower than Static Generation.

export async function getServerSideProps(context) {

  // you can do sth with ur context

  return {
    props: {
      // props for your component
    }
  }
}

context is an object,

containing like

params, req, res, preview...

Another Choice

Use case ?

SWR : A React hook lib from Next.js

Private and User-Specific Pages

Like User Dashboard

import useSWR from 'swr'

function Profile() {
  const { data, error } = useSWR('/api/user', fetch)

  if (error) return <div>failed to load</div>
  if (!data) return <div>loading...</div>
  return <div>hello {data.name}!</div>
}

Dynamic Routing

getStaticPaths

export async function getStaticPaths() {
  return {
    paths: [
      { params: { ... } } // See the "paths" section below
    ],
    fallback: true or false // Not introduce this time
  };
}

export const getStaticProps: GetStaticProps = async ({ params }) => {
  // get { params: { ... } } here
  return {
    props: {
	  ...
    }
  }
}

next/router

Access the router object by useRouter

import { useRouter } from 'next/router'

function ActiveLink({ children, href }) {
  const router = useRouter()
 
  const handleClick = (e) => {
    e.preventDefault()
    router.push(href)
  }

  return (
    <a href={href} onClick={handleClick}>
      {router.pathname}
    </a>
  )
}

export default ActiveLink

See here for more details.

To get metadata of the route, like pathname

 

To use router action, like push, replact

API Routes

Build API endpoints with Serveless Functions

// req = HTTP incoming message, res = HTTP server response
export default function handler(req, res) {
  // ...
}

/pages/api/handler.js

Use Case?

  1. Basic Auth
  2. Cache
  3. Proxy for CORS
  4. Cookie

Deploy with Vercel

What is Vercel?

The Jamstack deployment platform.
( Built by the creators of Next.js )

Support

  • Static deployment
  • JAMstack deployment
  • Serveless functions

Features

  • Custom Domains
  • Environmental Variables
  • Automatic HTTPs

The DPS  workflow of Next.js

D for Develop

S for Ship

P for Preview

Writing code in Next.js

Vercel will automatically ship main update to production

Not only code reviews, but deployment reviews

Vercel bot will follow each pull request     and create a preview URL

Next.js v11

next/lint

Support Optimal UX from Google's Web Platform team

Built-in Next-specific ESlint to ensure best practice

  • optimal loading
  • core web vitals(SEO)
  • security
  • accessibility

next/script

Third-Party Scripts Optimization

Automatically prioritize loading of third-party scripts

<Script
  src="url"
  strategy="beforeInteractive" // lazyOnload, afterInteractive
/>

<Script
  src={url} // consent mangagement
  strategy="beforeInteractive"
  onLoad={() => {
    // If loaded successfully, then you can load other scripts in sequence
  }}
/>

Three Strategy for Scripts

BeforeInteractive

AfterInteractive (default)

lazyOnLoad

Injected into HTML and run before bundled JS

  like bot detection

Inject on the client-side and run after hydration

Wait to load during idle time, like chat support

next/image

Auto Size Detection

Blur placeholders

import Image from 'next/image'
import author from '../public/me.png'

export default function Home() {
  return (
    // When importing the image as the source, you
    // don't need to define `width` and `height`.
    <Image src={author} alt="Picture of the author" />
  )
}

Default width and height would Reduce layout shift

Loading state maybe blink

Also support dynamic blurURL  ( blurha.sh)

<Image
  src="https://nextjs.org/static/images/learn.png"
  blurDataURL="data:image/jpeg;base64,/9j/2wBDAAYEBQYFBAYGBQYHBwYIChAKCgkJChQODwwQFxQYGBcUFhYaHSUfGhsjHBYWICwgIyYnKSopGR8tMC0oMCUoKSj/2wBDAQcHBwoIChMKChMoGhYaKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCgoKCj/wAARCAAIAAoDASIAAhEBAxEB/8QAFQABAQAAAAAAAAAAAAAAAAAAAAb/xAAhEAACAQMDBQAAAAAAAAAAAAABAgMABAUGIWEREiMxUf/EABUBAQEAAAAAAAAAAAAAAAAAAAMF/8QAGhEAAgIDAAAAAAAAAAAAAAAAAAECEgMRkf/aAAwDAQACEQMRAD8AltJagyeH0AthI5xdrLcNM91BF5pX2HaH9bcfaSXWGaRmknyJckliyjqTzSlT54b6bk+h0R//2Q=="
  alt="Picture of the author"
  placeholder="blur"
/>

A New Babel Loader for Webpack 5

Optimizing loading

Adding in-memory config caching layer

Improve Startup time

Next.js Live ( Waiting for early access )

Use Service Worker, WebAssembly, and ES Modules

It act like figma 👇

So, should we use Next?

Yes, but it depends.

The Concerns of Next

  1. The performance of the server from Next
  2. HTML Cache? 👉 Maybe CDN
  3. Highly Dynamic Site Case
  4. ...🤔💭

Some Usecases for Rytass

  1. Landing Page
  2. Compaign Page ( like unfilter )
  3. Official Site or 前台 (like NTCH Official )
  4. 後台(?)

For Better DX and Optimization

Thank for Listening

References

Made with Slides.com