| name | pages-deployment |
| description | Use when user asks about Pages deployment, Pages Functions, framework support, Next.js, Nuxt, Astro, SvelteKit, Remix, or Hono on Cloudflare. Also use when user says Pages デプロイ, フレームワーク, SSR, 静的サイト. Cloudflare Pages のデプロイメントガイドで、Pages Functions、フレームワーク対応(Next.js, Nuxt, Astro, SvelteKit, Remix, Hono)、ビルド設定、プレビュー環境を提供する。 |
| context | fork |
Cloudflare Pages Deployment
概要
Cloudflare Pages は静的サイトとフルスタックアプリケーションのホスティングプラットフォーム。
Git 連携による自動デプロイ、Pages Functions(Workers 統合)、プレビュー環境を提供。
2025年現在、Pages と Workers の境界は事実上消滅し、フルスタックエッジアプリとして統合。
デプロイ方法
Wrangler CLI
npx wrangler pages deploy ./dist
npx wrangler pages deploy ./dist --project-name my-site
npx wrangler pages deploy ./dist --branch preview
Git 連携
Cloudflare ダッシュボードで GitHub/GitLab を接続:
- リポジトリ選択
- ビルドコマンド・出力ディレクトリ設定
- 自動デプロイ有効化
Pages Functions
ディレクトリ構造
project/
├── functions/ # Functions ディレクトリ(必須)
│ ├── index.ts # → /
│ ├── hello.ts # → /hello
│ ├── api/
│ │ ├── data.ts # → /api/data
│ │ └── users/
│ │ └── [id].ts # → /api/users/:id
│ ├── _middleware.ts # ミドルウェア
│ └── [[path]].ts # キャッチオール
└── public/ # 静的アセット
ルーティング
| パターン | ファイル | マッチ |
|---|
| 静的 | functions/hello.ts | /hello |
| 動的 | functions/posts/[id].ts | /posts/123 |
| キャッチオール | functions/api/[[path]].ts | /api/a/b/c |
ハンドラー
export const onRequestGet: PagesFunction<Env> = async (context) => {
const userId = context.params.id;
const user = await context.env.DB.prepare(
"SELECT * FROM users WHERE id = ?"
).bind(userId).first();
if (!user) {
return new Response("Not found", { status: 404 });
}
return Response.json(user);
};
export const onRequestPost: PagesFunction<Env> = async (context) => {
const body = await context.request.json();
return Response.json({ success: true });
};
export const onRequest: PagesFunction<Env> = async (context) => {
return new Response(`Method: ${context.request.method}`);
};
ミドルウェア
export const onRequest: PagesFunction<Env> = async (context) => {
const auth = context.request.headers.get("Authorization");
if (!auth && context.request.url.includes("/api/")) {
return new Response("Unauthorized", { status: 401 });
}
const response = await context.next();
response.headers.set("X-Custom-Header", "value");
return response;
};
context オブジェクト
interface EventContext<Env> {
request: Request;
env: Env;
params: Record<string, string>;
waitUntil(promise: Promise<unknown>): void;
passThroughOnException(): void;
next(): Promise<Response>;
data: Record<string, unknown>;
}
フレームワーク対応
対応状況
| フレームワーク | 方式 | SSR | ISR | 備考 |
|---|
| Next.js | OpenNext + Workers | ○ | ○ | App Router 完全対応 |
| Nuxt 3 | Pages 直接 | ○ | ○ | Nitro プリセット |
| Astro | @astrojs/cloudflare | ○ | - | アダプター必須 |
| SvelteKit | @sveltejs/adapter-cloudflare | ○ | - | |
| Remix | Pages 直接 | ○ | - | エッジネイティブ |
| Hono | Workers/Pages | ○ | - | 最も親和性高 |
Next.js(OpenNext)
2025年推奨: OpenNext + Cloudflare Workers
npm create cloudflare@latest my-next-app -- --framework=next
npx open-next@cloudflare build
npx wrangler deploy
対応機能:
- App Router
- React Server Components
- Server Actions
- ISR(Incremental Static Regeneration)
- 画像最適化
Nuxt 3
ゼロ設定でデプロイ可能:
nuxt build
nuxt generate
npx wrangler pages deploy .output/public
export default defineNuxtConfig({
nitro: {
preset: "cloudflare-pages",
},
});
Astro
npx astro add cloudflare
import cloudflare from "@astrojs/cloudflare";
export default defineConfig({
output: "server",
adapter: cloudflare(),
});
SvelteKit
npm install -D @sveltejs/adapter-cloudflare
import adapter from "@sveltejs/adapter-cloudflare";
export default {
kit: {
adapter: adapter(),
},
};
Remix
npx create-cloudflare@latest my-remix-app -- --framework=remix
Hono
最も Cloudflare に最適化されたフレームワーク:
npm create cloudflare@latest my-app -- --template hono
import { Hono } from "hono";
const app = new Hono();
app.get("/", (c) => c.text("Hello Hono!"));
app.get("/api/users/:id", async (c) => {
const id = c.req.param("id");
const user = await c.env.DB.prepare(
"SELECT * FROM users WHERE id = ?"
).bind(id).first();
return c.json(user);
});
export default app;
wrangler.toml 設定
Pages 用設定
name = "my-pages-app"
compatibility_date = "2025-01-01"
pages_build_output_dir = "dist"
[vars]
API_URL = "https://api.example.com"
[[d1_databases]]
binding = "DB"
database_name = "my-db"
database_id = "xxx"
[[kv_namespaces]]
binding = "KV"
id = "xxx"
[[r2_buckets]]
binding = "BUCKET"
bucket_name = "my-bucket"
環境別設定
[env.preview]
vars = { API_URL = "https://staging-api.example.com" }
[env.production]
vars = { API_URL = "https://api.example.com" }
プレビュー環境
自動生成
- プルリクエストごとに自動で一意の URL が生成
https://<hash>.<project>.pages.dev
ブランチ指定
npx wrangler pages deploy ./dist --branch feature-x
プレビュー保護
Cloudflare Access でプレビュー URL を保護可能。
ビルド設定
ダッシュボード設定
| 設定 | 例 |
|---|
| ビルドコマンド | npm run build |
| ビルド出力ディレクトリ | dist / .next / .output/public |
| ルートディレクトリ | / または apps/web |
環境変数
| 場所 | 用途 |
|---|
| ダッシュボード | 本番シークレット |
.dev.vars | ローカル開発 |
wrangler.toml の [vars] | 非機密設定 |
ビルド環境変数(自動設定)
| 変数 | 説明 |
|---|
CF_PAGES | Pages ビルドかどうか |
CF_PAGES_BRANCH | ブランチ名 |
CF_PAGES_COMMIT_SHA | コミットハッシュ |
CF_PAGES_URL | デプロイ URL |
Advanced Mode
Pages Functions のルーティングが不十分な場合、_worker.js を直接配置:
export default {
async fetch(request, env) {
const url = new URL(request.url);
if (url.pathname.startsWith("/assets/")) {
return env.ASSETS.fetch(request);
}
if (url.pathname.startsWith("/api/")) {
return handleApi(request, env);
}
return env.ASSETS.fetch(new Request(
new URL("/index.html", request.url),
request
));
},
};
カスタムドメイン
設定方法
- ダッシュボードで「カスタムドメイン」追加
- DNS レコードが自動設定(Cloudflare DNS の場合)
- SSL 証明書が自動発行
手動 DNS 設定
外部 DNS の場合:
CNAME www <project>.pages.dev
制限事項
| 項目 | 制限 |
|---|
| ビルド時間 | 20分(Free)/ 30分(Pro) |
| ファイルサイズ | 25MB/ファイル |
| ファイル数 | 20,000ファイル |
| Functions | Workers と同じ制限 |
| ビルド数 | 500/月(Free)/ 5000/月(Pro) |
公式リソース