Next.js超简洁完整篇
1、Next.js认识
👉 官方网站
js
// Next.js官网
https://nextjs.org/
// Next.js 中文网
https://next.nodejs.cn/
👉先来看看我们环境要求
js
系统环境需求
Node.js 12.22.0 或更高版本
MacOS、Windows (包括 WSL) 和 Linux 都被支持
这里我本地使用的依然是node20.12.0
👉Next.js是什么
Next.js 是一个基于 React 的轻量级框架,提供了服务器端渲染(SSR)、静态站点生成(SSG)、API 路由
也就是说对应的就是Nuxt(Vue全家桶系列),而Next.js算是React与之对应的
👉Next.js优点
服务器端渲染(SSR)
Next.js 支持将页面预渲染为 HTML,在服务器端发送到浏览器。提高页面加载和 SEO
静态站点生成(SSG)
在构建时我们可以生成静态 HTML 文件,加快站点的加载速度
API 路由
在 Next.js 中API 路由能让我们在一个项目中实现前端和后端的功能
代码拆分
Next.js 会为每个页面进行代码拆分,仅加载当前页面需要的 JavaScript,提升性能。
文件系统路由
Next.js 使用文件系统作为路由机制
支持 TypeScript 和 CSS-in-JS
Next.js 内置对 TypeScript 和 CSS-in-JS(如 styled-components)的支持。
2、Next项目安装创建
👉环境要求
Node.js 18.17或更高版本。
js
`https://nodejs.cn/`
支持 macOS、Windows(包括 WSL)和 Linux。
👉搭建运行
js
npx create-next-app@latest
# or
yarn create next-app@latest xxx
npx create-next-app@latest nexusnext (这里我采用的构建方式)
安装时看到以下提示:
js
Need to install the following packages:
[email protected]
Ok to proceed? (y) y
// 选择y 就是需要装一些东西
// 下面 是我选择的部分
Ok to proceed? (y) y
√ Would you like to use TypeScript? ... No / Yes //Yes采用
√ Would you like to use ESLint? ... No / Yes // No未采用
√ Would you like to use Tailwind CSS? ... No / Yes //Yes采用
√ Would you like your code inside a `src/` directory? ... No / Yes //Yes采用
√ Would you like to use App Router? (recommended) ... No / Yes //Yes采用
√ Would you like to use Turbopack for `next dev`? ... No / Yes //Yes采用
√ Would you like to customize the import alias (`@/*` by default)? ... No / Yes //Yes采用
√ What import alias would you like configured? ... @/* //Yes采用
3、运行项目
这个时候我们已经安装好了依赖了,就可以进行启动了
js
yarn dev

这个时候我们的项目已经启动了
4、打包部署
Next.js给我们提供了四种方式的部署
Deployment Option | Feature Support |
---|---|
Node.js server | All |
Docker container | All |
Static export | Limited |
Adapters | Platform-specific |
接下来我们就尝试最简单直接的静态部署
我们打包到github pages进行静态托管
👉 设置静态部署方式
next.config.mjs中只需要将output 方式设置为静态模式
js
/** @type {import('next').NextConfig} */
const nextConfig = {
output: 'export',
};
export default nextConfig;
👉指定静态文件输出目录
next.config.js=> nextConfig=> distDir
js
/** @type {import('next').NextConfig} */
const nextConfig = {
distDir: 'out', // 指定静态文件输出目录为 out
output: 'export',
};
export default nextConfig;
👉 打包
js
yarn build
打包以后文件结构如图

👉预览本地打包的静态文件
js
// 安装http-server
npm install -g http-server
//进入打包目录启动本地 HTTP 服务器
cd out
http-server -p 3000
接下来就可以点击提示我们生成的地址查看项目了,也可以将根目录=> out目录下面的文件部署到任何地方
js
http://127.0.0.1:3000
5、Next.js结构搭建
👉默认目录
Next.js 使用文件系统路由,这意味着应用中的路由由你构建文件的方式决定
默认的时候已经帮我们创建了 app/
文件夹,添加了 layout.tsx
和 page.tsx
文件
当用户访问应用的根目录 (/
) 时,将渲染这些内容
🍎 app下面目录结构以及代表的含义
js
布局(layout.js)
模板(template.js)
加载状态(loading.js)
错误处理(error.js)
404(not-found.js)
//目录以及代表的含义
pages/:这个目录用于存放页面组件。每个文件都会自动成为一个路由。
public/:这个目录用于存放静态文件,如图片、字体等。
styles/:这个目录用于存放样式文件。
components/:这个目录用于存放可复用的组件
🍎搭建常见的目录结构
src下面新建文件夹以及结构如下
js
my-next-ts-project/
│
├── public/ # 公共文件夹(放置静态资源)
│ ├── images/ # 图片资源
│ ├── favicon.ico # 网站图标
│ └── robots.txt # 机器人文件,控制爬虫抓取规则
│
├── src/ # 源代码
│ ├── assets/ # 静态资源(如图片、字体等)
│ ├── components/ # 组件(按功能划分的可复用组件)
│ ├── pages/ # 页面(每个文件对应一个路由)
│ │ ├── _app.tsx # 自定义的 App 组件,用于页面的初始化
│ │ ├── _document.tsx # 自定义文档(如果有需要)
│ │ ├── index.tsx # 首页(默认路由)
│ │ ├── about.tsx # 关于页面
│ │ └── contact.tsx # 联系页面
│ ├── styles/ # 样式文件(CSS, SASS, 或 CSS 模块)
│ │ ├── globals.css # 全局样式
│ │ └── Home.module.css # 主页特有样式(可以是 CSS 模块)
│ ├── utils/ # 工具函数(帮助类文件)
│ ├── services/ # API 服务(与后端接口相关的文件)
│ ├── hooks/ # 自定义 React hooks
│ ├── contexts/ # React context 管理
│ └── config/ # 配置文件(例如环境变量、项目配置)
│
├── .env # 环境变量配置
├── .gitignore # Git 忽略文件
├── next-env.d.ts # TypeScript 环境类型文件
├── next.config.js # Next.js 配置文件
├── package.json # 项目信息和依赖
├── tsconfig.json # TypeScript 配置文件
└── README.md # 项目说明文件
👉配置next.config.ts
根目录
next.config.ts=> NextConfig=> srcDir
配置以后我们的根目录就是src目录了
js
import type { NextConfig } from "next";
const nextConfig: NextConfig = {
/* config options here */
srcDir: 'src', // 指定源码目录为 src
distDir: 'dist', // 指定静态文件输出目录为 out
output: 'export',
};
export default nextConfig;
👉首页搭建
next默认的首页就是 pages/page.tsx
,默认的pages/page.tsx
如下图
🍎layout.tsx
js版本的时候
js
export default function RootLayout({ children }) {
return (
<html lang="en">
<body>{children}</body>
</html>
)
}
写成ts
js
export default function RootLayout({children}: {children: React.ReactNode}) {
return (
<html lang="en">
<body>{children}</body>
</html>
)
}
配置项目跟目录src在 next.config.ts之中以后
🍎首页内容pages=> index.tsx
这个就是我们的首页
js
// src/app/page.tsx
import React from 'react';
import Header from '../components/Header';
import Footer from '../components/Footer';
const Home: React.FC = () => {
return (
<div>
<Header />
<main style={{ padding: '40px', textAlign: 'center' }}>
<h1>Welcome to My Website</h1>
<p>This is the homepage of our awesome website!</p>
</main>
<Footer />
</div>
);
};
export default Home;
🍎头部Footer.tsx
js
// src/components/Footer.tsx
import React from 'react';
const Footer: React.FC = () => {
return (
<footer style={{ marginTop: '40px', padding: '20px', backgroundColor: '#222', color: 'white' }}>
<p>© 2025 My Website. All Rights Reserved.</p>
</footer>
);
};
export default Footer;
🍎底部Header.tsx
js
// src/components/Header.tsx
import React from 'react';
const Header: React.FC = () => {
return (
<header>
<nav>
<ul style={{ listStyleType: 'none', display: 'flex', gap: '20px' }}>
<li><a href="/">Home</a></li>
<li><a href="/about">About</a></li>
<li><a href="/services">Services</a></li>
<li><a href="/contact">Contact</a></li>
</ul>
</nav>
</header>
);
};
export default Header;
搭建以后初步预览

接下来我们就可以继续完善我们的项目
6、Next.js 路由
👉搭建二级目录以及多级目录
我们新建目录和文件如下图所示:
js
src\app\about
src\app\about\contact.tsx //联系我们
src\app\about\service.tsx //服务我们
我们想有个关于我们,里面有个联系我们和服务我们,这两个页面均使用about下的公共组件,如何实现呢?
建立如下图的文件路径
js
src\app
\about
layout.tsx //控制访问about下的公共组件
page.tsx //控制访问about显示
\about\services\page.tsx //控制访问about=>services显示
\about\contact\page.tsx //控制访问about=>contact显示
🍎 默认页面(page.tsx)
page.tsx为我们默认的页面,访问目录的时候一般就直接访问这个里面的内容
js
// pages/about/index.tsx
import React from 'react';
const About: React.FC = () => {
return (
<div>
<h1>关于我们</h1>
<p>这里是关于我们的页面内容。</p>
</div>
);
};
export default About;
🍎 定义布局(layout.tsx)
布局是指多个页面共享的 UI。在导航的时候,布局会保留状态,保持可交互性并且不会重新渲染,比如用来实现后台管理系统的侧边导航栏。
定义一个布局,Next.js默认给我们每个文件下一个 layout.js
的文件可以存放当前目录的公共组件部分,该文件默认导出一个 React 组件,该组件应接收一个 children
prop,chidren
表示子布局(如果有的话)或者子页面。
js
// pages/about/Layout.tsx
import React from 'react';
interface AboutLayoutProps {
children: React.ReactNode;
}
const AboutLayout: React.FC<AboutLayoutProps> = ({ children }) => {
return (
<div>
我是about的一级
<main style={{ padding: '40px', textAlign: 'center' }}>
{children}
</main>
</div>
);
};
export default AboutLayout;
🍎 二级子菜单
内容位于\about\services\page.tsx
js
export default function Service() {
return (
<div>我是关于about=》服务</div>
)
}
通过这种方式我们就可以达到无限控制二级菜单以及更多子级菜单的效果
👉路由跳转
在Next之中我们如何跳转路由呢
🍎Link跳转
js
//引入
import Link from 'next/link'
//使用
<li><a href="/about">About</a></li>
🍎动态路由
我们也可拼接动态路由来展示我们的内容部分
js
// 动态路由
<Link href="/post/[id]" as={`/post/${post.id}`}>
<a>{post.title}</a>
</Link>
7、Next.js 主题以及配置
👉使用不同的主题
这里很简单,假如我们采用自定义样式的方式,只需要更改主题最顶部的data-theme
名称即可
js
'use client'
import Image from "next/image";
import React, { useEffect, useState } from 'react';
export default function Home() {
const [theme, setTheme] = useState<'light' | 'dark' | 'default'>('default'); // 'light' or 'dark'
useEffect(() => {
// 根据 theme 状态切换 data-theme
document.documentElement.setAttribute('data-theme', theme);
}, [theme]);
return (
<div>
<main style={{ padding: '40px', textAlign: 'center' }}>
<button onClick={() => setTheme('default')}>
Toggle Theme
</button>
<button onClick={() => setTheme('dark')}>
Toggle Theme
</button>
<button onClick={() => setTheme('light')}>
Toggle Theme
</button>
</main>
</div>
);
}
添加以后我们最顶部就成为了下面这样子
js
<html lang="en" data-theme="light">
然后针对不同的主题做样式
js
/* 默认主题 */
[data-theme='default'] {
--theme-color:#7F78FF; /* 默认主题 */
--primary-color: #2c3e50; /* 深色主题的主色 */
--secondary-color: #1abc9c; /* 深色主题的次色 */
}
/* 主题切换:深色主题 */
[data-theme='dark'] {
--primary-color: #2c3e50; /* 深色主题的主色 */
--secondary-color: #1abc9c; /* 深色主题的次色 */
}
/* 主题切换:浅色主题 */
[data-theme='light'] {
--primary-color: #3498db; /* 浅色主题的主色 */
--secondary-color: #2ecc71; /* 浅色主题的次色 */
}
使用这个主题定义的颜色
js
👉 使用客户端
在next之中我们使用的服务端渲染,如果需要使用一些客户端的hooks,需要在顶部添加识别即可
js
'use client'
8、部署上线
👉部署github pages
🍎修改next.config.ts 文件
js
import type { NextConfig } from "next";
const nextConfig: NextConfig = {
distDir: 'dist', // 指定静态文件输出目录为 out
output: 'export',
basePath: '/nexus', // 替换为你的 GitHub 仓库名
assetPrefix: '/nexus/', // 替换为你的 GitHub 仓库名
};
export default nextConfig;
🍎安装部署需要的依赖
js
安装 GitHub Pages 依赖
为了将构建的静态文件部署到 GitHub Pages,你需要安装 gh-pages 包:
npm install gh-pages --save-dev
yarn add gh-pages --save-dev
🍎在 package.json
中添加脚本
需要注意next export
已经移除了
js
"scripts": {
"dev": "next dev --turbopack",
"build": "next build",
"start": "next start",
"lint": "next lint",
// "predeploy": "next build && next export", 错误 删掉 已经移除next export
"deploy": "gh-pages -d dist"
},
🍎 打包部署
js
yarn build
yarn deploy
这个时候我们项目已经成功部署了,访问远程即可操作我们的仓库了
报错提示
👉 children规定类型报错
js
./src/app/admin/layout.tsx:13:3
Type error: Binding element 'children' implicitly has an 'any' type.
11 |
12 | export default function DashboardLayout({
> 13 | children,
| ^
14 | }) {
15 | const pathname = usePathname();
16 | console.log(pathname,'Nav-地址');
error Command failed with exit code 1.
原因
主要是children类型为any报错
解决方法
进行约束即可
js
// 旧的写法
export default function DashboardLayout({
children,
}) {
//新的约束写法
export default function DashboardLayout({
children,
}: {children: React.ReactNode}) {}