Next.js 初学者指南
关注我!:关注@EricTheCoder_
什么是 Next.js?
它是一个 React 前端开发 Web 框架,支持服务器端渲染和静态站点生成等功能。
服务器端渲染?
在传统的 React 应用中,整个应用都在客户端加载和渲染。Next.js 允许首次加载的页面由服务器渲染,这对于 SEO 和性能都非常有利。
Next.js 的其他优势
- 轻松的页面路由
- 服务器 Api 路由
- 静态站点生成(如 Gatsby)
- 轻松部署
创建 Next.js 第一个项目
要安装和创建 Next.js 项目,您可以使用方便的 node npx 命令“create-next-app my-app-name”
$ npx create-next-app my-app-name
或者使用 Tailwind CSS 预配置
$ npx create-next-app -e with-tailwindcss my-app-name
这将创建一个文件夹并创建启动 Next.js 应用程序所需的所有文件、配置和一切内容。
应用程序创建后,您可以启动它
$ cd your-app-name
$ npm run dev
这将启动你的 Next.js 空应用。默认情况下,已为你创建了一个欢迎页面。
页面和路由
在 Next.js 中,我们不必使用路由库来管理路由。
Next.js 路由非常容易实现。
当您使用 create-next-app 命令创建新的 Next.js 应用程序时,该应用程序默认创建一个名为“pages”的文件夹
这个“pages”文件夹是你的路由管理文件夹。因此,文件夹中的每个 React 组件文件都将被视为一个特定的路由。
例如,如果文件夹包含这些文件:
- index.js
- about.js
- blog.js
该文件将通过 3 种方式自动转换:
- 索引页 localhost/index
- 关于页面 localhost/about
- 博客页面 localhost/blog
正如您所见,原理非常简单。
此外,如果您访问不存在的路线,例如“localhost/home”,Next.js 将自动显示未找到的 404 页面
这里是 about.js 页面的示例。如你所见,该页面没有任何具体说明。它只是一个普通的 React 函数式组件。
function AboutPage() {
return (
<div>
<h1>About</h1>
</div>
)
}
export default AboutPage
嵌套路由
那么像 localhost/blog/contact 这样的嵌套路由怎么样?
要创建嵌套路由,您需要创建一个子文件夹。
例如:pages/blog
在该文件夹中,您可以创建“contact.js”反应组件,这将创建页面 localhost/blog/contact
如果您在该子文件夹中创建 index.js 文件,Next.js 将使用该组件来表示您的根路由。例如:localhost/blog 将呈现 pages/blog/index.js
如果您在 pages/blog.js 中创建一个文件,并在 pages/blog/index.js 中创建另一个文件。它们都代表同一个 localhost/blog 路由。在这种情况下,Next.js 将仅渲染 blog.js 文件。
那么动态路线呢?每个博客文章都有自己的路线:
- 本地主机/博客/我的第一个博客
- 本地主机/博客/我的第二篇博客文章
在 Next.js 中,您可以使用括号符号创建动态路由。
例如:pages/blog/[slug].js
是的,在文件名中包含括号看起来有点奇怪,但这就是方法。
如果可以使用 useRoute 钩子从路由中提取 slug 变量。
这是 [slug].js 页面的示例
import { useRouter } from 'next/router'
function PostPage() {
const router = useRouter()
return (
<div>
<h1>My post: {router.query.slug}</h1>
</div>
)
}
export default PostPage
这是一个基本的例子。在实际应用中,slug 变量将用于加载帖子文件或在数据库中查找相应的帖子。
路线链接
现在你已经创建了第一个路由。我想你一定想知道如何将页面链接到这些路由吧?为此,你需要使用“next/link”
这里是主页的示例,其中包含指向“关于”页面的链接:
import Link from 'next/link'
export default function Home() {
return (
<div>
<h1>Home</h1>
<Link href="about">About</Link>
</div>
)
}
在“关于”页面中,如果您想创建一个返回主页的链接,您可以输入:
<Link href="/">Home</Link>
如果您想要设置链接样式,则必须使用以下语法:
<Link href='/about'>
<a className="text-blue-500">About this project</a>
</Link>
路由重定向
如果你想强制重定向到特定页面怎么办?比如点击按钮?你可以使用 router.push 来实现:
import Link from 'next/link'
import { useRouter } from 'next/router'
function About() {
const router = useRouter()
return (
<div>
<h1>About Page</h1>
<p>This is the about page</p>
<button onClick={() => router.push('/')}>Return to home</button>
</div>
)
}
您将组件放在哪里?
通常你会想要创建一个组件或布局文件。例如,一个用于渲染导航栏的组件。
到目前为止,我们只使用了 pages 文件夹。如果你不想让你的组件成为路由页面,该怎么办?你不想让用户打开类似 localhost/navbar 这样的页面。
如果您将 Navbar.js 组件放入 pages 文件夹中,就会附加这些内容。
那该怎么办呢?很简单,你需要把所有“非页面”组件放在另一个文件夹中。
按照惯例,大多数 Next.js 使用文件夹名称“components”,并且该文件夹在应用程序的根文件夹中创建。
例如,如果您想创建一个布局组件,您可以在新的组件文件夹中进行创建:/components/Layout.js
该 React 组件可以在应用程序的任何位置使用,但需要作为路由页面引用。
头部组件
Next.js 服务器端渲染第一个页面加载。为此,它会操作页面的 HTML,包括 header 部分。
要提供标题部分标签(如标题或元标签),您需要使用 Next.js Head 组件。
以下是使用 Head 组件的 Layout 组件的示例。
// components/Layout.js
import Head from 'next/head'
function Layout({title, keywords, description, children}) {
return (
<div>
<Head>
<title>{title}</title>
<meta name='description' content={description}/>
<meta name='keywords' content={keywords}/>
</Head>
{children}
</div>
)
}
export default Layout
Layout.defaultProps = {
title: 'This is my app title',
description: 'This is my app description',
keywords: 'web, javascript, react, next'
}
自定义 404 未找到页面
您可以创建自定义的 404 未找到页面。您可以自定义消息或添加您自己的页面布局。
在 pages 文件夹中创建 404.js 文件。
当遇到 404 时,Next.js 将自动重定向到此页面。
以下是自定义 404 页面的示例:
// pages/404.js
import Layout from '../components/Layout'
function NotFoundPage() {
return (
<Layout>
Sorry the page you are looking is no where to be found.
</Layout>
)
}
export default NotFoundPage
导入快捷方式别名
随着您的应用程序越来越大,某些组件可能会嵌套在应用程序文件夹结构的深处。
import Layout from '../../components/Layout'
可以创建一个快捷方式来帮助您节省一些按键并获得如下结果:
import Layout from '@/components/Layout'
@char 是一种快捷语法。
要创建此快捷方式及更多内容,您需要在应用程序的根目录下创建一个名为“jsconfig.json”的文件:
// jsconfig.json
{
"compilerOptions": {
"baseUrl": ".",
"paths": {
"@/components/*": ["components/*"],
}
}
}
服务器端数据获取
Next.js 无需在客户端获取数据,而是可以
在页面中启用服务器端渲染并允许您进行初始数据填充,这意味着发送已从服务器填充数据的页面。
要实现服务器端数据获取,您有两个选择:
- 每次请求时获取数据
- 在构建时仅获取一次数据(静态站点)
每次请求时获取数据
要对每个请求进行服务器端渲染,您需要使用 getServerSideProps 函数。
您可以在组件文件的末尾添加此功能:
export async function getServerSideProps() {
const res = await fetch(`http://server-name/api/items`)
const items = await res.json()
return {
props: {items},
}
}
如果您的组件文件中存在该函数,Next.js 将自动使用 getServerSideProps 对象填充您的组件道具。
在构建时获取数据
要在构建时进行服务器端渲染,您需要使用 getStaticProps 函数。
您可以在组件文件的末尾添加此功能:
export async function getStaticProps() {
const res = await fetch('http://server-name/api/items')
const items = await res.json()
return {
props: {items},
}
}
您可能还希望在构建时获取数据,但采用动态路径(例如 /posts/my-first-post)
假设我们有一个页面名称 posts/[slug].js
这将为您提供 posts/my-first-post、posts/my-second-blog 等路线。
在这种情况下,您可以使用 getStaticPaths 在构建时创建所有这些子路由
export async function getStaticPaths() {
const res = await fetch(`${API_URL}/posts`)
const posts = await res.json()
const paths = posts.map(post => ({params: {slug: post.slug}}))
return {
paths,
fallback: true,
}
}
export async function getStaticProps({params: {slug}}) {
const res = await fetch(`${API_URL}/posts?slug=${slug}`)
const posts = await res.json()
return {
props: {
post: posts[0]
}
}
}
图像优化
Next.js 具有内置的图像组件和自动图像优化功能。
Next.js 图像组件 next/image 是 HTML 元素的扩展,专为现代网络而开发。
默认情况下,图片会延迟加载。这意味着页面速度不会因为图片超出视口范围而受到影响。图片会在滚动到视口时加载。
首先导入图像组件:
import Image from 'next/image'
在您的组件中使用它:
<Image
src="/image.png"
alt="Picture of the author"
width={500}
height={500}
/>
如果您想了解有关 Next.js 图像组件的更多信息,可以阅读官方文档:https://nextjs.org/docs/api-reference/next/image
结论
今天就到这里。我还有很多关于 React 的文章,所以如果你想确保不会错过任何内容,请点击关注我!
关注我!:关注@EricTheCoder_
文章来源:https://dev.to/ericchapman/next-js-beginner-s-guide-8l3