在 Next.js App Router 中使用仅在服务端的代码

React Server Components 架构将组件分为客户端和服务端类型,并与 Next.js 的 App Router 集成。

使用 App Router 进行开发时,区分服务端代码和客户端代码对于应用程序的安全性、性能和可维护性至关重要。这篇博文将介绍在 Next.js 应用程序中定义服务端代码。

服务器端代码

Next.js 中的 Server-only code 是指仅在服务器端执行的代码。这可能包括以下模块或功能:

  • 使用特定于服务器的库
  • 访问包含敏感信息的环境变量
  • 与数据库或外部 API 交互
  • 处理机密业务逻辑

之所以会出现这样的挑战,是因为 JavaScript 模块可以在服务器和客户端组件之间共享,从而导致服务器端代码无意中包含在客户端包中。这种包含可能会暴露敏感数据、增加捆绑包大小并导致潜在的安全漏洞。

实践示例

让我们通过一个实践示例来演示服务端代码。首先使用 create-next-app 创建 Next.js 应用程序。然后,在你创建的 src/utils 目录中,添加一个名为 server-utils.ts 的文件。该文件将包含以下服务端函数:

js 复制代码
// src/utils/server-utils.ts
export const serverSideFunction = () => {
  console.log(
    `Using multiple libraries,
     accessing environment variables,
     interacting with a database,
     processing confidential information`
  );
  return "Server-side result";
};

想象一下这个函数使用各种 NPM 包、访问 API 密钥、从数据库检索数据并处理敏感算法。这样的函数永远不应该暴露给客户端。

现在,让我们在服务器组件中使用此函数,例如"关于"页面组件:

js 复制代码
// pages/about.tsx
import { serverSideFunction } from "@/utils/server-utils";

const About = () => {
  const result = serverSideFunction();
  console.log(result);
  return <div>About Page</div>;
};

export default About;

导航到 /about 路径,你将在服务器终端(而不是浏览器)中观察到日志消息,这表明我们的代码仅适用于服务器。

但是,如果此函数被错误地导入到客户端组件(例如仪表板页面)中怎么办?该代码可能部分或完全不起作用。这就是 server-only 包发挥作用的地方。

使用 server-only

为了保护我们的应用程序,我们安装 server-only 包:

shell 复制代码
npm i server-only

然后我们修改 server-utils.ts 以包含此包:

js 复制代码
// src/utils/server-utils.ts
import 'server-only';

export const serverSideFunction = () => {
  console.log(
    `Using multiple libraries,
     accessing environment variables,
     interacting with a database,
     processing confidential information`
  );
  return "Server-side result";
};

现在,如果有人尝试将 serverSideFunction 导入客户端组件,构建过程将抛出错误,从而防止服务器端代码泄漏到客户端。

使用 client-only

正如服务端代码需要隔离一样,与特定于浏览器的功能(如 DOM、窗口对象、localStorage 等)交互的仅客户端代码也必须限制在客户端,以有效地利用特定于浏览器的功能。

client-only 包充当护栏,确保我们的客户端代码保留在其所属的位置。

总结

在 Next.js 应用程序中,保持服务端代码和客户端代码之间的清晰界限至关重要。它确保你的应用程序的完整性、安全性和用户体验。使用 server-onlyclient-only 包并遵循最佳实践来加强这种分离并保护你的应用程序。

相关推荐
前端大卫43 分钟前
Vue3 + Element-Plus 自定义虚拟表格滚动实现方案【附源码】
前端
却尘1 小时前
Next.js 请求最佳实践 - vercel 2026一月发布指南
前端·react.js·next.js
ccnocare1 小时前
浅浅看一下设计模式
前端
Lee川1 小时前
🎬 从标签到屏幕:揭秘现代网页构建与适配之道
前端·面试
Ticnix1 小时前
ECharts初始化、销毁、resize 适配组件封装(含完整封装代码)
前端·echarts
纯爱掌门人2 小时前
终焉轮回里,藏着 AI 与人类的答案
前端·人工智能·aigc
twl2 小时前
OpenClaw 深度技术解析
前端
崔庆才丨静觅2 小时前
比官方便宜一半以上!Grok API 申请及使用
前端
星光不问赶路人2 小时前
vue3使用jsx语法详解
前端·vue.js
天蓝色的鱼鱼2 小时前
shadcn/ui,给你一个真正可控的UI组件库
前端