前端转全栈 10:Node 通用后端——Express / Fastify 与何时需要独立服务
系列目录:本文是「前端转全栈:Next.js + Supabase 实战」系列的第 10 篇。前面都在 Next.js 里写服务端,这一篇补上「通用 Node 后端」概念——它是你能力闭环里不可或缺的一块。
Next.js 很强,但有些场景它不合适:长连接、重型后台任务、需要独立扩缩容的服务、或非 Web 的 TCP/WebSocket 服务。这时你需要一个独立的 Node 服务。好消息:你已会 JS/TS,迁移成本极低。
一、最小 Express 服务
npm init -y && npm i express
// server.ts
import express from "express"
const app = express()
app.use(express.json()) // 中间件:解析 JSON body
app.get("/api/health", (_req, res) => res.json({ ok: true }))
app.post("/api/comments", (req, res) => {
const { content } = req.body
if (!content) return res.status(400).json({ error: "content 必填" })
// ...写库
res.status(201).json({ content })
})
app.listen(3001, () => console.log("listen on 3001"))
运行 tsx server.ts(或 node server.js),访问 localhost:3001/api/health。你会发现和第 4 篇的 Route Handler 思路一模一样——只是换了壳。
二、中间件模型:贯穿请求的一串「拦截器」
Express/Fastify 的核心是中间件(middleware):每个请求依次穿过一串函数,可读取/修改 req、决定是否继续。
// 日志中间件
app.use((req, _res, next) => {
console.log(`${req.method} ${req.url}`)
next() // 必须调用 next() 才往下走,否则请求挂起
})
// 鉴权中间件(可复用于多个路由)
function requireAuth(req: any, res: any, next: any) {
const token = req.headers.authorization?.replace("Bearer ", "")
if (!token) return res.status(401).json({ error: "未登录" })
req.user = verifyToken(token)
next()
}
app.get("/api/me", requireAuth, (req, res) => res.json(req.user))
这正是 Next.js 中间件、createServerClient 里 cookie 处理的同源思想——请求处理是一层套一层的管道。
三、Fastify:更快、更现代的替代
Fastify 是 Express 的精神续作,性能更高、内置 schema 校验(类似 zod):
import Fastify from "fastify"
const app = Fastify()
app.get("/api/health", async () => ({ ok: true }))
app.listen({ port: 3001 })
选型建议:小项目 Express 生态最熟;追求性能/TypeScript 体验选 Fastify。两者理念相通,学会一个另一个秒懂。
四、WebSocket:真正的实时
HTTP 一问一答,不适合聊天、协作光标、行情推送。WebSocket 建立后长连接双向通信:
import { WebSocketServer } from "ws"
const wss = new WebSocketServer({ port: 3002 })
wss.on("connection", (ws) => {
ws.on("message", (msg) => {
// 广播给所有连接
wss.clients.forEach((c) => c.send(msg.toString()))
})
})
前端用 new WebSocket("ws://localhost:3002") 接收推送。这正是 Supabase Realtime 的底层模型——你用 Supabase 时它已帮你封装好,但理解 WebSocket 让你知道「实时」是怎么发生的。
五、什么时候需要独立 Node 后端?
| 场景 | 用 Next.js 够吗 | 建议 | |------|---------------|------| | 普通 CRUD Web 应用 | ✅ 够 | 就用 Next.js + Supabase | | 需要 WebSocket 长连接 | ⚠️ 勉强(可用 Route Handler + 外部 ws) | 独立 Node 服务 | | 重型后台任务(视频转码等) | ❌ | 独立 worker 服务 | | 给多个前端/移动端共享的 API | ✅ 也可 | Next.js 也能做,但独立更清晰 | | 已有微服务架构 | ❌ | 独立后端 |
结论:大多数前端转全栈的项目,Next.js + Supabase 一条龙就够。但当你遇到长连接、后台任务、独立扩缩容时,知道怎么写个 Express/Fastify 服务就是「全栈」和「只会框架」的分水岭。
总结
- 独立 Node 服务与 Next.js Route Handler 思路同源,迁移成本低。
- 中间件 = 贯穿请求的一串拦截器,可复用鉴权/日志。
- WebSocket 解决 HTTP 做不到的实时双向通信。
- 大多数项目 Next.js + Supabase 足矣;长连接/重任务才需要独立后端。
下一篇讲缓存与性能——让你的全栈应用扛得住量。
练习:用 Express 写一个
/api/todos的 CRUD(内存数组即可),加上express.json()和日志中间件,用curl测通增删查。感受「独立后端」的掌控感。
Comments
Sign in to leave a comment.