Ankita.eth
GithubContact
  • About Ankita
  • experience
    • TECHNOLOGIES
    • Frontend
      • Javascript
      • React
      • NextJS
      • HTML & CSS
      • UI Libraries & Frameworks
        • Tailwind CSS
        • Comprehensive Guide to UI Libraries and Frameworks
    • Backend
      • Node.js
      • Express.js
    • Database
      • Mongodb, Mongoose
      • PostgresSQl
      • MySQL
    • Packege Mangers
      • NPM-Node Packege Manager
      • Yarn
      • Yarn 2 (Berry)
      • PNPM
      • BUN
      • Commands cheatsheet
    • API Providers
      • Alchemy
      • Telegram Bot
      • CoinMarket
      • Thirdweb
      • Infura
      • Moralis
    • DevOps/Infrastructure
      • Docker
      • Kubernetes
      • CI/CD
      • Docker Swam
    • Protocols
      • ERCs & EIPs
        • ERC-20
        • ERC-721
        • ERC-1155
        • ERC-4337
        • ERC-6551
        • ERC-777
        • ERC-3643
        • EIP-7702
        • ERC-7715
        • ERC-7739
        • EIP-6780
        • EIP-5792
        • ERC-4626
        • EIP-1559
        • ERC-404
        • ERC-3643
        • ERC-223
    • Web3 Toolkits
      • Foundry
      • Hardhat
      • RemixIDE
    • Messaging/Caching
      • Kafka
      • Redis
      • Sendgrid
    • Blockchain
      • Solana
      • Ethereum
      • Polygon & Zero knowldge Proof
      • Bitcoin
      • Solidity
    • Deployment Platforms
      • AWS
      • Vercel
      • Heroku, Render
      • Domain setup
  • SDKs
    • Google Cloud SDK
    • AWS SDK
    • Firebase SDK
  • EOF EVM Object Format
  • Articles
    • Medium Articles
    • 🌐 My Work
  • 📞 Get in Touch
Powered by GitBook
On this page
  • Next.js: A Comprehensive Guide 🚀
  • Introduction to Next.js 📚
  • Next.js Architecture 🏗️
  • Example Project Structure
  • User Flow in a Next.js Application 🔄
  • Core Next.js Concepts and Code Snippets 💻
  • TypeScript Integration 🧰
  • Built-In CSS and Sass Support 🎨
  • Advantages of Using Next.js with TypeScript 🚀
  • Component Lifecycle in Next.js 🔄
  • Real-time Example: Building a Blog with Next.js 📝
  • FAQs🧠
  • Conclusion 🎉

Was this helpful?

  1. experience
  2. Frontend

NextJS

Next.js: A Comprehensive Guide 🚀

Introduction to Next.js 📚

Next.js is a powerful React framework that enables you to build server-side rendered and statically generated web applications. It was introduced by Vercel (formerly Zeit) in 2016 to address common challenges in React development and to provide a more opinionated, yet flexible, structure for building modern web applications.

Why Next.js? 🤔

Next.js offers several advantages over traditional React applications:

  • Server-Side Rendering (SSR) for improved performance and SEO

  • Static Site Generation (SSG) for blazing-fast static websites

  • Automatic code splitting for faster page loads

  • Built-in CSS support

  • API routes for building backend functionality

  • Easy deployment and scalability

Next.js vs Other Frameworks 🥊

Compared to other frameworks, Next.js stands out in several ways:

Feature
Next.js
Create React App
Gatsby

Server-Side Rendering

✅

❌

❌

Static Site Generation

✅

❌

✅

API Routes

✅

❌

❌

Automatic Code Splitting

✅

✅

✅

Zero Configuration

✅

✅

❌

Next.js Architecture 🏗️

Next.js follows a hybrid architecture that combines server-side rendering, static site generation, and client-side rendering. Here's a high-level overview:

Example Project Structure

Here is an example structure for a Next.js project with TypeScript:

my-next-app/
│
├── public/
│   └── image.jpg
│
├── pages/
│   ├── api/
│   │   └── hello.ts
│   ├── about.tsx
│   ├── index.tsx
│   └── posts/
│       └── [id].tsx
│
├── styles/
│   └── globals.css
│
├── tsconfig.json
└── package.json

User Flow in a Next.js Application 🔄

Here's a typical user flow in a Next.js application:

Core Next.js Concepts and Code Snippets 💻

1. Pages and Routing

Next.js uses a file-system based routing. Each file inside the pages directory becomes a route.

// pages/index.js
export default function Home() {
  return <h1>Welcome to Next.js!</h1>
}

// pages/about.js
export default function About() {
  return <h1>About Us</h1>
}

2. Dynamic Routes

You can create dynamic routes using brackets [] in the filename.

// pages/posts/[id].js
import { useRouter } from 'next/router'

export default function Post() {
  const router = useRouter()
  const { id } = router.query

  return <p>Post: {id}</p>
}

3. API Routes

API routes allow you to build your API endpoints as Node.js serverless functions.

// pages/api/hello.js
export default function handler(req, res) {
  res.status(200).json({ name: 'John Doe' })
}

4. Data Fetching

Next.js provides several methods for data fetching:

getStaticProps (Static Generation)

export async function getStaticProps() {
  const res = await fetch('<https://api.example.com/data>')
  const data = await res.json()

  return {
    props: { data },
  }
}

export default function Home({ data }) {
  return <div>{data.title}</div>
}

getServerSideProps (Server-side Rendering)

export async function getServerSideProps(context) {
  const res = await fetch(`https://api.example.com/data/${context.params.id}`)
  const data = await res.json()

  return {
    props: { data },
  }
}

export default function Post({ data }) {
  return <div>{data.title}</div>
}

5. Custom App Component

Use _app.js to initialize pages with custom layouts or global state.

// pages/_app.js
import '../styles/globals.css'

function MyApp({ Component, pageProps }) {
  return (
    <Layout>
      <Component {...pageProps} />
    </Layout>
  )
}

export default MyApp

5. Image Optimization in Next.js 🖼️

Next.js provides built-in image optimization features through the Image component:

import Image from 'next/image'

function MyImage() {
  return (
    <Image
      src="/images/profile.jpg"
      alt="Profile picture"
      width={500}
      height={500}
    />
  )
}

This component automatically optimizes images for better performance and user experience.

TypeScript Integration 🧰

Next.js has excellent TypeScript support out of the box. To use TypeScript in your Next.js project:

npx create-next-app@latest --typescript
# or
yarn create next-app --typescript

TypeScript Configuration (tsconfig.json)

Next.js automatically creates a tsconfig.json file with recommended settings:

{
  "compilerOptions": {
    "target": "es5",
    "lib": ["dom", "dom.iterable", "esnext"],
    "allowJs": true,
    "skipLibCheck": true,
    "strict": true,
    "forceConsistentCasingInFileNames": true,
    "noEmit": true,
    "esModuleInterop": true,
    "module": "esnext",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "isolatedModules": true,
    "jsx": "preserve",
    "incremental": true
  },
  "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
  "exclude": ["node_modules"]
}

Built-In CSS and Sass Support 🎨

Next.js supports CSS and Sass out of the box. You can import CSS files directly in your components:

import styles from './Button.module.css'

export function Button() {
  return (
    <button className={styles.error}>
      Delete
    </button>
  )
}

Advantages of Using Next.js with TypeScript 🚀

  • Enhanced developer experience with better autocomplete and type checking

  • Reduced runtime errors through static type checking

  • Improved code maintainability and readability

  • Better integration with IDEs for refactoring and navigation

Here's an example of a TypeScript component in Next.js:

import { NextPage } from 'next'
import { useState } from 'react'

interface Props {
  initialCount: number
}

const Counter: NextPage<Props> = ({ initialCount }) => {
  const [count, setCount] = useState(initialCount)

  return (
    <div>
      <p>Count: {count}</p>
      <button onClick={() => setCount(count + 1)}>Increment</button>
    </div>
  )
}

export default Counter

Component Lifecycle in Next.js 🔄

Next.js components follow the React component lifecycle with some additional hooks specific to server-side rendering:

1. Mounting

  • constructor(): Initialize state and bind methods

  • render(): Render the component

  • componentDidMount(): Perform side effects after component is mounted

2. Updating

  • shouldComponentUpdate(): Decide if the component should re-render

  • render(): Re-render the component

  • componentDidUpdate(): Perform side effects after component updates

3. Unmounting

  • componentWillUnmount(): Clean up before component is unmounted

4. Next.js Specific Lifecycle Methods

  • getInitialProps(): Fetch data on the server (deprecated in favor of getStaticProps and getServerSideProps)

  • getStaticProps(): Fetch data at build time for static generation

  • getServerSideProps(): Fetch data on each request for server-side rendering

Example: Component Lifecycle

import React from 'react'

class LifecycleComponent extends React.Component {
  constructor(props) {
    super(props)
    this.state = { count: 0 }
    console.log('Constructor')
  }

  static async getInitialProps() {
    console.log('getInitialProps')
    return { initialCount: 5 }
  }

  componentDidMount() {
    console.log('Component Did Mount')
    this.setState({ count: this.props.initialCount })
  }

  shouldComponentUpdate(nextProps, nextState) {
    console.log('Should Component Update')
    return nextState.count !== this.state.count
  }

  componentDidUpdate() {
    console.log('Component Did Update')
  }

  componentWillUnmount() {
    console.log('Component Will Unmount')
  }

  render() {
    console.log('Render')
    return (
      <div>
        <h1>Count: {this.state.count}</h1>
        <button onClick={() => this.setState(state => ({ count: state.count + 1 }))}>
          Increment
        </button>
      </div>
    )
  }
}

export default LifecycleComponent

Real-time Example: Building a Blog with Next.js 📝

Let's create a simple blog application to demonstrate Next.js features:

1. Set up the project

npx create-next-app my-blog
cd my-blog

2. Create a layout component

// components/Layout.js
import Link from 'next/link'

export default function Layout({ children }) {
  return (
    <div>
      <nav>
        <Link href="/">Home</Link>
        <Link href="/about">About</Link>
      </nav>
      <main>{children}</main>
      <footer>© 2024 My Blog</footer>
    </div>
  )
}

3. Update _app.js to use the layout

// pages/_app.js
import Layout from '../components/Layout'

function MyApp({ Component, pageProps }) {
  return (
    <Layout>
      <Component {...pageProps} />
    </Layout>
  )
}

export default MyApp

4. Create an API route for blog posts

// pages/api/posts.js
const posts = [
  { id: 1, title: 'Hello Next.js', content: 'This is my first post!' },
  { id: 2, title: 'Learning Next.js', content: 'Next.js is awesome!' },
]

export default function handler(req, res) {
  res.status(200).json(posts)
}

5. Update the home page to display blog posts

// pages/index.js
import Link from 'next/link'

export async function getServerSideProps() {
  const res = await fetch('<http://localhost:3000/api/posts>')
  const posts = await res.json()
  return { props: { posts } }
}

export default function Home({ posts }) {
  return (
    <div>
      <h1>My Blog</h1>
      <ul>
        {posts.map(post => (
          <li key={post.id}>
            <Link href={`/posts/${post.id}`}>{post.title}</Link>
          </li>
        ))}
      </ul>
    </div>
  )
}

6. Create a dynamic route for individual blog posts

// pages/posts/[id].js
import { useRouter } from 'next/router'

export async function getServerSideProps({ params }) {
  const res = await fetch(`http://localhost:3000/api/posts`)
  const posts = await res.json()
  const post = posts.find(p => p.id === parseInt(params.id))
  return { props: { post } }
}

export default function Post({ post }) {
  const router = useRouter()

  if (router.isFallback) {
    return <div>Loading...</div>
  }

  return (
    <div>
      <h1>{post.title}</h1>
      <p>{post.content}</p>
    </div>
  )
}

FAQs🧠

  1. What is the purpose of the getStaticProps function in Next.js?

    Answer: getStaticProps is used to fetch data at build time for static generation. It allows you to pre-render pages with dynamic content by fetching data and passing it as props to the page component.

  2. How does Next.js handle routing?

    Answer: Next.js uses a file-system based routing. Each file inside the pages directory automatically becomes a route. For example, pages/about.js will be accessible at /about.

  3. What is the difference between getServerSideProps and getStaticProps?

    Answer: getServerSideProps runs on every request and is used for server-side rendering, while getStaticProps runs at build time and is used for static site generation.

  4. How can you create dynamic routes in Next.js?

    Answer: Dynamic routes in Next.js are created by using square brackets [] in the filename. For example, pages/posts/[id].js will match /posts/1, /posts/2, etc.

  5. What is the purpose of the _app.js file in Next.js?

    Answer: The _app.js file is used to initialize pages. It can be used to add global styles, layouts, or state management that should be applied to all pages in the application.

Conclusion 🎉

Next.js provides a powerful and flexible framework for building modern web applications. Its server-side rendering capabilities, coupled with static site generation and API routes, make it an excellent choice for a wide range of projects. TypeScript integration further improves code quality and development efficiency, making this combination an excellent choice for both small and large-scale projects. By mastering Next.js, you'll be well-equipped to create fast, scalable, and SEO-friendly web applications.


PreviousReactNextHTML & CSS

Last updated 9 months ago

Was this helpful?