作者:Kapeel Kokane ✏️
在6 月 15 日举行的2021 Next.js Conf上,来自世界各地的开发者齐聚一堂,共同见证了 Vercel 团队最新版本Next.js 11的发布。Next.js 11 中包含的更新和新功能对已经流行的库进行了重大改进。
在本文中,我们将深入研究其中一些对用户和开发人员体验都产生影响的更新。让我们开始吧!
一致性
就其核心而言,一致性是一组原则或编码指南,它将一些决策责任从开发人员手中夺走。通过设置默认值和提供指导方针,更容易实现预期结果并防止常见错误。
根据Next.js 团队的说法,“一致性是一个系统,它提供精心设计的解决方案和规则以支持最佳加载和 Core Web Vitals”。
Next.js 11 中的新一致性原则可以分为三个方面:
1. 强默认值
框架必须在其核心建立某些设计模式,使开发人员难以做错事。
2. 可操作的规则
尽管有很强的默认设置,但有时开发人员有责任在两条潜在路径之间进行选择。一组可操作的规则将使应用程序更容易遵守强大的性能标准,同时仍然允许足够的自定义级别。
3. 创作时间
创作时间更重视功能开发周期而非生产后的性能。在代码提交之前必须考虑性能,而不是在产品发布后将其视为基于分析的指标。
强制执行创作时间原则的最简单方法之一是通过 linting 规则。因此,Next.js 11 开箱即用地支持 ESLint。
要获得这些功能的好处,您必须通过运行以下代码升级到 Next.js 的最新版本:
npm i next@latest react@latest react-dom@latest
通过运行以下代码启用 linting:
npx next lint
一旦我们升级我们的版本并启用 ESLint,我们将开始收到警告,这些警告会促使我们朝着行业最佳实践的方向发展,帮助我们的应用程序遵守一致性准则。
脚本优化
许多网站都包含第三方脚本以启用分析和广告。
加载脚本的顺序对页面性能有巨大影响,尤其是在处理网页上的多个外部脚本时。如果管理不当,脚本会严重降低用户体验。
Next.js 引入了一个脚本组件,它的strategy
属性可以处理很多这些问题。
让我们来测试一下!一个明显的变化是我们不再需要在标签中包装原生 HTML 脚本next/head
标签:
import Head from 'next/head'
function Home() {
return (
<>
<Head>
<script async src="https://polyfill.io/v3/polyfill.min.js?features=WebAnimations" />
</Head>
</>
)
}
相反,我们可以直接使用原生 HTML 脚本标签,如下所示:
import Script from 'next/script'
function Home() {
return (
<>
<Script src="https://polyfill.io/v3/polyfill.min.js?features=WebAnimations" />
</>
)
}
在这个例子中,我们建议使用该beforeInteractive
策略加载我们的 polyfill 。让我们改变策略,看看它如何影响加载脚本!
beforeInteractive
脚本在服务器端被注入到 HTML 中,并在捆绑的 JavaScript 运行之前在浏览器上运行。使用下面的代码块,我们看到获取 polyfill 的网络调用是在网络选项卡中的其他所有内容之前进行的:
<Script src="https://polyfill.io/v3/polyfill.min.js?features=WebAnimations"
`strategy="beforeInteractive" />
afterInteractive
如果我们将策略更改为afterInteractive
,脚本将在页面变为交互式后执行。网络请求位于网络选项卡中的页面底部,它优先考虑更重要的任务。
lazyOnload
将策略更改为lazyOnload
告诉 Next.js 在空闲时间加载脚本。获取 polyfill 的网络请求进一步向下移动到页面底部;没有其他延迟加载的脚本,如下面的屏幕截图所示。
onLoad
属性
除了上面的自定义之外,如果我们想在脚本加载后执行一些代码,我们可以使用onLoad
脚本标签的prop。该onLoad
属性可确保上面的脚本加载,使功能使用脚本的功能和变量没有崩溃:
<Script
id="my-script"
src="https://polyfill.io/v3/polyfill.min.js?features=WebAnimations"
onLoad={() => {
// this executes after the script is loaded
}}
/>
图像改进
Next.js 11 包括对next/image
组件的增强,例如减少布局偏移,为最终用户提供更流畅的体验。
静态图像的尺寸检测
以前,要使用Image
组件渲染图像,必须使用height
和width
道具。这些道具允许 Next.js 识别图像的大小并渲染占位符,防止布局偏移和混乱的用户界面:
<Image
alt="Fixing"
src="/fixing.png"
layout="intrinsic"
width={700}
height={475}
/>
Next.js 11 提供了对src
prop 的支持,可以使用import
关键字来应用。如果以这种方式导入源,则不需要单独指定height
和width
道具:
import source from '../public/fixing.png'
<Image
alt="Fixing"
src={source}
layout="intrinsic"
/>
图像占位符
在 Next.js 11 中,该next/image
组件支持一个新的占位符属性,该属性设置value
为blur
较慢的连接。该next/image
组件将在加载原始图像时显示模糊的低分辨率图像:
<Image
alt="Fixing"
src={source}
layout="intrinsic"
placeholder="blur"
/>
在最终加载原始图像之前,模糊图像将显示两到三秒钟。
此外,Next.js 11 提供了通过Image
标签提供自定义占位符的选项,可以使用blurDataURL
prop 显示。提供给此道具的值可以使用诸如blurha.sh 之类的应用程序生成。
Webpack 5 默认支持
Webpack 5 支持在 10.2 版中宣布,适用于所有文件中没有自定义 webpack 配置的 Next.js 项目next.config.js
。自定义 webpack 配置如下所示:
module.exports = {
webpack: (config, { buildId, dev, isServer, defaultLoaders, webpack }) => {
return config; // return the modified config
},
}
从版本 11 开始,无论自定义配置如何,webpack 5 都是所有 Next.js 应用程序的默认构建工具。webpack 5 附带的所有以下优化将可用于新建项目。
改进的磁盘缓存
我们知道我们可以使用命令触发构建next build
。但是,如果我们为项目触发的两个连续构建之间几乎没有变化怎么办?
Webpack 5 只允许有条件地重新编译已更改的文件。性能得到了提高,因为我们不会冗余处理尚未更改的块。
改进的快速刷新
有了 webpack 5,Next.js 11 将快速刷新识别为一项特殊任务,并以更高的优先级执行它,从而在每次保存任何代码更改时都能更快地刷新。
长期 asset 缓存
使用 webpack 5,build
命令的构建过程是确定性的。如果代码段没有更改,则后续构建时生成的哈希不会更改,这意味着在浏览器中散列的文件可以在更长的时间内重复使用。
改进的 tree shaking
Webpack 5 提供了tree shaking commonJS
模块的功能,从包中删除未使用的代码。
从 Create React App 迁移
由于社区的要求,Vercel 团队推出了该@next/codemod
工具,该工具支持 React 和 Next.js 项目之间的兼容性。
我们可以运行该工具,为它提供一个使用 Create React App 脚本生成的项目,并将其转换为 Next.js 项目。让我们试试吧!
首先,使用以下命令创建一个 React 应用程序:
npx create-react-app cra-demo
现在,我们已经初始化了一个新的 React 项目,我们可以使用以下命令运行我们的项目:
npm run start
你会看到熟悉的 React 屏幕:
接下来,运行脚本以从 Create React App 迁移到 Next.js 项目:
npx @next/codemod cra-to-next cra-demo
我们可以看到脚本对存储库进行了一些更改以将其移植到 Next.js。这些变化包括:
- 对脚本的更改
package.json
- 添加
pages
文件夹,这是 Next.js 存储库的主要功能 - 更改通过创建
_app.js
文件导入 CSS 的方式 - 创建
next.config.js
文件并填充它
Babel优化
Next.js 11 为 webpack 提供了全新的Babel 加载器实现,其中包括一个内存配置缓存层,通过 10.1 和 10.2 版本的改进进一步缩短了启动时间。
Next.js Live
Vercel 的团队使用了多种下一代前端技术,如 serviceWorker、WebAssembly 和 ES 模块,以在浏览器内部提供协作环境。使用 Next.js Live 功能,开发人员和设计人员只需共享 URL 即可协作。Live 功能目前正在抢先体验下运行。
结论
很明显,这些升级构成了有史以来最突出的 Next.js 版本之一!
对内核进行了一些更改以减少启动时间,例如 Babel 优化,以及促使开发人员采用经过验证的解决方案的一致性建议。其他改进是加载图像和脚本,使用户体验无缝。此外,我们现在可以使用 Live 功能改进协作。
由于这些以及更多原因,Next.js 11 版本看起来很有希望并且值得升级。试一试,让我们知道你在评论中的想法!