关于 bun-nextjs
bun-nextjs 是面向 Next.js 开发者的技能,介绍使用 Bun 进行开发、构建和运行应用,并涵盖 Bun API 用法与依赖安装安全。
主要功能
- 01使用 Bun 运行 Next.js
- 02配置开发、构建与启动命令
- 03在服务端使用 Bun API
- 04安全安装依赖
- 05部署与常见错误排查
适用场景
- 01创建并启动 Next.js 项目
- 02在服务组件或 API 路由中使用 bun:sqlite
- 03检查依赖安装安全设置
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ secondsky/ claude-skills --skill bun-next.js安装后在 Claude Code 中输入/bun-next.js确认已加载。
详细介绍
Bun Next.js
使用 Bun 运行 Next.js 应用,加快开发和构建速度。
快速开始
# Create new Next.js project with Bun
bunx create-next-app@latest my-app
cd my-app
# Install dependencies
bun install
# Development
bun run dev
# Build
bun run build
# Production
bun run start
安全安装
bunx create-next-app 等脚手架工具会下载并执行远程代码。在多个安装环境(本地、Docker)中,都需要固定版本。运行前,请遵循供应链安全最佳实践:
- 阻止安装后脚本 — Bun 默认禁用这些脚本;可在
package.json的trustedDependencies中允许指定的包 - 冷却期 — 在
bunfig.toml中配置minimumReleaseAge,等待新版本发布 7 天 - 安装前审计 — 运行
socket package score npm <pkg>,或使用socket npm install <pkg>检查包
加载 dependency-upgrade 技能,查看完整的安全配置,包括 Socket CLI 集成、冷却期设置、锁文件验证和 CI 强制执行。
项目设置
package.json
{
"scripts": {
"dev": "next dev",
"build": "next build",
"start": "next start",
"lint": "eslint ."
},
"dependencies": {
"next": "^16.2.0",
"react": "^19.2.0",
"react-dom": "^19.2.0"
}
}
使用 Bun 作为运行时
{
"scripts": {
"dev": "bun --bun next dev",
"build": "bun --bun next build",
"start": "bun --bun next start"
}
}
--bun 标志会强制 Next.js 使用 Bun 运行时,而不是 Node.js。
配置
next.config.js
/** @type {import('next').NextConfig} */
const nextConfig = {
// Turbopack is the default bundler in Next.js 16 (top-level, not under experimental)
turbopack: {},
// Server-side Bun APIs
serverExternalPackages: ["bun:sqlite"],
// Note: a `webpack` key is no longer supported in Next.js 16 — Turbopack is the
// default bundler and a `webpack` config will fail `next build`. Bun-specific
// imports (`bun:sqlite`, `bun:ffi`) are handled via `serverExternalPackages`
// above. If you truly need the webpack bundler, run `next build --webpack`.
};
module.exports = nextConfig;
在 Next.js 中使用 Bun API
服务端组件
// app/page.tsx (Server Component)
import { Database } from "bun:sqlite";
export default async function Home() {
const db = new Database("data.sqlite");
const users = db.query("SELECT * FROM users").all();
db.close();
return (
<div>
{users.map((user) => (
<p key={user.id}>{user.name}</p>
))}
</div>
);
}
API 路由
// app/api/users/route.ts
import { Database } from "bun:sqlite";
export async function GET() {
const db = new Database("data.sqlite");
const users = db.query("SELECT * FROM users").all();
db.close();
return Response.json(users);
}
export async function POST(request: Request) {
const body = await request.json();
const db = new Database("data.sqlite");
db.run("INSERT INTO users (name) VALUES (?)", [body.name]);
db.close();
return Response.json({ success: true });
}
文件操作
// app/api/files/route.ts
export async function GET() {
const file = Bun.file("./data/config.json");
const config = await file.json();
return Response.json(config);
}
export async function POST(request: Request) {
const data = await request.json();
await Bun.write("./data/config.json", JSON.stringify(data, null, 2));
return Response.json({ saved: true });
}
服务端操作
// app/actions.ts
"use server";
import { Database } from "bun:sqlite";
import { revalidatePath } from "next/cache";
export async function createUser(formData: FormData) {
const name = formData.get("name") as string;
const db = new Database("data.sqlite");
db.run("INSERT INTO users (name) VALUES (?)", [name]);
db.close();
revalidatePath("/users");
}
export async function deleteUser(id: number) {
const db = new Database("data.sqlite");
db.run("DELETE FROM users WHERE id = ?", [id]);
db.close();
revalidatePath("/users");
}
代理(以前称为中间件)
在 Next.js 16 中,middleware.ts 已更名为 proxy.ts(middleware 名称仍然可用,但已弃用)。代理在 Node.js 运行时运行,而不是 Edge 运行时。
⚠️ 通过 OpenNext 部署到 Cloudflare?请保留
middleware.ts。@opennextjs/cloudflare尚不能识别proxy.ts文件名——重命名会导致中间件在 Cloudflare 上被静默禁用。在 OpenNext 添加支持之前,请使用传统的middleware.ts部署(它在 Next 16 中仍然可用,只是在上游已弃用)。此注意事项不适用于 Node.js/Vercel/Bun 原生部署。
// proxy.ts (renamed from middleware.ts in Next.js 16)
import { NextResponse } from "next/server";
import type { NextRequest } from "next/server";
export function proxy(request: NextRequest) {
// Check auth
const token = request.cookies.get("token");
if (!token && request.nextUrl.pathname.startsWith("/dashboard")) {
return NextResponse.redirect(new URL("/login", request.url));
}
return NextResponse.next();
}
export const config = {
matcher: ["/dashboard/:path*"],
};
环境变量
# .env.local
DATABASE_URL=./data.sqlite
API_SECRET=your-secret-key
// Access in server components/actions
const dbUrl = process.env.DATABASE_URL;
const secret = process.env.API_SECRET;
// Expose to client (prefix with NEXT_PUBLIC_)
// .env.local
NEXT_PUBLIC_API_URL=https://api.example.com
部署
生产环境构建
bun run build
bun run start
Docker
FROM oven/bun:1
WORKDIR /app
COPY package.json bun.lockb ./
RUN bun install --frozen-lockfile
COPY . .
RUN bun run build
EXPOSE 3000
CMD ["bun", "run", "start"]
Vercel
# Install Vercel CLI
bun add -g vercel
# Deploy
vercel
注意:Vercel 的 Edge 运行时使用 V8,而不是 Bun。Bun API 可用于:
- 服务端组件(Node.js 运行时)
- API 路由(Node.js 运行时)
- 服务端操作(Node.js 运行时)
性能提示
-
Turbopack 在 Next.js 16 中为默认选项(无需标志):
bun run dev -
优先使用服务端组件 — 减少发送到客户端的 JavaScript
-
简单应用可使用 Bun SQLite,代替外部数据库
-
启用压缩:
// next.config.js module.exports = { compress: true, };
常见错误
| 错误 | 原因 | 解决方法 |
|---|---|---|
Cannot find bun:sqlite | 运行时错误 | 使用 bun --bun next dev |
Module not found | 缺少依赖 | 运行 bun install |
Hydration mismatch | 服务端/客户端差异 | 检查数据获取 |
Edge runtime error | 在 Edge 上使用 Bun API | 使用 Node.js 运行时 |
何时加载参考资料
遇到以下情况时,加载 references/app-router.md:
- App Router 模式
- 路由组
- 并行路由
遇到以下情况时,加载 references/caching.md:
- 数据缓存策略
- 重新验证模式
- 静态生成