搬離 next-on-pages,改用 @opennextjs/cloudflare

Cloudflare 九月底把 next-on-pages 專案封存,issue 全關,npm package 棄用,不再維護了,建議大家改用 OpenNext 的 Cloudflare adapter。
太無情了吧,哪有這樣說換就換的…… 只能搬家了。
轉換提要
原本 next-on-pages 是把 Next.js 的產出轉換成可以在 Cloudflare Pages 平台上跑的東西,改用 @opennextjs/cloudflare 的話,主要就是改成轉給 Cloudflare Workers 而已。
文件參考:
- Migrate from Pages to Workers · Cloudflare Workers docs
- Get Started - Existing Next.js apps - OpenNext
基本開發環境不變
因為開發時仍然是用 Next.js 自己的 next dev
,所以受 pages 或 workers 影響較小。
程式變更
-
不再使用 edge runtime
現在反而是只支援 node.js runtime,還不支援 edge,幸好 edge 是比較弱的,問題相對少。
我是單純移除所有的
export const runtime = 'edge';
即可。 -
套件當然要換掉
安裝
@opennextjs/cloudflare@latest
取代@cloudflare/next-on-pages
和eslint-plugin-next-on-pages
(相關的東西也都刪掉)。 -
取得開發環境的 Cloudflare binding 資源
開發時必須取得 local 的 CF 資源(D1 資料庫、R2 儲存空間等),在
next.config.mjs
裡面,以前是用:
要改成:import { setupDevPlatform } from '@cloudflare/next-on-pages/next-dev';
import { initOpenNextCloudflareForDev } from "@opennextjs/cloudflare";
-
DB 要在每個請求中動態取得
參考 Db - OpenNext。 有些 ORM 會受影響,像我是用 drizzle-orm,以前可以直接設一個 global db,現在要改成
getDb()
,幸好改起來還算單純。
設定檔變更: .open-next.config.ts
第一次跑 opennextjs-cloudflare build
會建立這個設定檔,內容如下:
// default open-next.config.ts file created by @opennextjs/cloudflare
import { defineCloudflareConfig } from "@opennextjs/cloudflare/config";
import r2IncrementalCache from "@opennextjs/cloudflare/overrides/incremental-cache/r2-incremental-cache";
export default defineCloudflareConfig({
incrementalCache: r2IncrementalCache,
});
那個 r2IncrementalCache
是 Next.js 快取會用到的,參考文件,視情況可能還有 DO和 D1 的 binding 會跑出來?
設定檔變更: wrangler.jsonc
原本的 "pages_build_output_dir": "./dist"
要拿掉,然後我增加的部分如下:
"main": ".open-next/worker.js",
"assets": {
"directory": ".open-next/assets",
"binding": "ASSETS"
},
"r2_buckets": [
{
"binding": "(原本在用的 binding 名,這桶是原本就有的)",
"bucket_name": "(原本在用的 bucket 名,原本就有)"
},
{
"binding": "NEXT_INC_CACHE_R2_BUCKET",
"bucket_name": "feeders-next-inc-cache(自己命名,這個只是舉例)"
}
],
"preview_urls": true,
"observability": {
"enabled": true,
"head_sampling_rate": 1
},
"workers_dev": true,
其中 main
和 assets
是必要的。
NEXT_INC_CACHE_R2_BUCKET
是跟前述 build 出來的 .open-next.config.ts 對應,這個 bucket 要另外手動開出來。
build、預覽和部署
以前用 pnpm next-on-pages --outdir=dist
build 到 dist 目錄,
現在換成 pnpm opennextjs-cloudflare build
,會 build 到 .open-next 目錄,可以觀察一下生成的檔案內容。
原本用 wrangler pages
開頭的指令都要換掉,改成例如 wrangler deploy
等。
Production 的環境變數
以前我是將 production 的環境變數通通當成 secret 上傳到 Cloudflare,不然要維護本地的 .dev.vars
、Next.js 的 .env.*
、寫在 wrangler config 中的變數、…… 等等有點麻煩。
現在雖然建議管理方式仍是在 CF 後台設定變數或 secret,
但我發現 opennextjs build 會直接把所有環境的 .env.*
都包進去:
opennextjs-cloudflare/packages/cloudflare/src/cli/build/open-next/compile-env-files.ts#L4
所以除非 build 的時候有隔離這些 .env 檔案,不然其實 worker 是吃得到變數的。 實測確實如此,且這些變數在 CF 後台也看不見。
參考文件: Env Vars - OpenNext
網址 xxx.pages.dev 沒了
沒救,可憐,現在附送的網址是 xxx.workers.dev
,還是買個自己的網域吧。
實際 commits
這次轉換的是 feeders 專案,相關 commit 可以看: Commits 10/2 ~ 10/5 · bootleq/feeders
有 0 個意見
☂