Open10

Cloudflare Pages

qatocoqatoco

git integration

https://developers.cloudflare.com/pages/get-started/git-integration/

qatocoqatoco

Get Started

https://developers.cloudflare.com/pages/framework-guides/nextjs/ssr/get-started/

# 新規
npm create cloudflare@latest -- my-next-app --framework=next
# 既存app
npm install --save-dev @cloudflare/next-on-pages
# wrangler.toml追加
touch wrangler.toml
# next.configへの追記
code ./next.config.mjs

wrangler.toml

next.config.追記(bindings利用に必須)

++  import { setupDevPlatform } from '@cloudflare/next-on-pages/next-dev';

// skip

/** @type {import('next').NextConfig} */
const nextConfig = {
// skip
};

++ if (process.env.NODE_ENV === 'development') {
++   await setupDevPlatform();
++  }
export default nextConfig;

Pagesでは edgeランタイムを指定

package.json にnpm scripts追記

// next build実行プラス、pages互換な形に変換
++ "pages:build": "npx @cloudflare/next-on-pages",
// wrangler pages dev = OSSのworkerランタイムでローカル実行
// next devは Node.jsランタイムでの実行
++ "preview": "npm run pages:build && wrangler pages dev",
// ビルド後にデプロイ実行
++ "deploy": "npm run pages:build && wrangler pages deploy"

デプロイ

  • automatic deoployment: pushしたらデプロイ
  • CLIで手動デプロイ: wrangler pages deploy

専用のeslintプラグイン

npm install --save-dev eslint-plugin-next-on-pages
{
  "extends": [
    "next/core-web-vitals",
++    "plugin:eslint-plugin-next-on-pages/recommended"
  ],
  "plugins": [
++    "eslint-plugin-next-on-pages"
  ]
}
qatocoqatoco

Bindingの活用

https://developers.cloudflare.com/pages/framework-guides/nextjs/ssr/bindings/

getRequestContext()

  • bindingsにアクセスできる
const { env, cf, ctx } = getRequestContext();

ts対応

install, tsconfig, env.d.ts

# インストール
npm install --save-dev @cloudflare/workers-types
# tsconfigのtypesに追記
code tsconfig.json
# binding データの型定義
touch env.d.ts
"types": [
++     "@cloudflare/workers-types/2024-07-29"
]
interface CloudflareEnv {
  MY_KV_1: KVNamespace;
  MY_KV_2: KVNamespace;
  MY_R2: R2Bucket;
  MY_DO: DurableObjectNamespace;
}

cf, cfx

qatocoqatoco

workerエントリポイント

https://developers.cloudflare.com/pages/framework-guides/nextjs/ssr/advanced/

// 構成
import nextOnPagesHandler from "@cloudflare/next-on-pages/fetch-handler";

export default {
  async fetch(request, env, ctx) {
    // do something before running the next-on-pages handler
    const response = await nextOnPagesHandler.fetch(request, env, ctx);
    // do something after running the next-on-pages handler
    return response;
  },
} as ExportedHandler<{ ASSETS: Fetcher }>;
# Q:automatic deploymentはこれで動くのか
npx @cloudflare/next-on-pages --custom-entrypoint=./custom-entrypoint.ts
qatocoqatoco

Caching、Revalidation

https://developers.cloudflare.com/pages/framework-guides/nextjs/ssr/caching/

qatocoqatoco

@cloudflare/next-on-pages がサポートする機能

https://developers.cloudflare.com/pages/framework-guides/nextjs/ssr/supported-features/

サポートしない機能

  • Node.js API
    • @opennextjs/cloudflare を使え。ただしメジャーリリース前
    • v1.0リリース後はこちらが推奨になる
      • Next.jsの新機能は Node.js APIを前提にしてるため
qatocoqatoco

https://developers.cloudflare.com/pages/framework-guides/nextjs/ssr/troubleshooting/

pages router使用時のランタイム指定

--  export const runtime = "edge";
++ export const runtime = 'experimental-edge';

not-found routeでのエラー対策

export const runtime = 'edge'

export default async function NotFound() {
    // ...
    return (
        // ...
    )
}
  • SSGで、generateStaticParams()/app 以下で使うとエラーに => dynamicParamsfalse

    • Node.jsランタイム向けにサーバレス関数が作成されてしまうため
  • トップレベル getRequestContext() はNG

  • SSGで /pages 以下で getStaticPaths() でエラー => fallback: false,