Cloudflare Workers Deployment
Deploy web applications to Cloudflare Workers with GitHub Actions automation.
Quick Start
- •Create
wrangler.jsoncat project root - •Create
workers/directory with Hono entry point - •Add GitHub Actions workflows
- •Set secrets via
wrangler secret put - •Configure GitHub secrets for CI/CD
Core Files
wrangler.jsonc
jsonc
{
"$schema": "node_modules/wrangler/config-schema.json",
"name": "app-name",
"main": "workers/index.ts",
"compatibility_date": "2025-01-01",
"compatibility_flags": ["nodejs_compat"],
"assets": {
"directory": "./dist/public/",
"binding": "ASSETS",
"not_found_handling": "single-page-application" // SPA routing: serve index.html for unknown paths
},
"vars": { "ENVIRONMENT": "development" },
"env": {
"preview": {
"name": "app-name-preview",
"vars": { "ENVIRONMENT": "preview" }
},
"production": {
"name": "app-name",
"vars": { "ENVIRONMENT": "production" }
}
}
}
Do NOT hardcode account_id - use CLOUDFLARE_ACCOUNT_ID env var in CI.
workers/index.ts
typescript
import { Hono } from "hono";
import type { Env } from "./env";
const app = new Hono<{ Bindings: Env }>();
app.get("/healthz", (c) => c.json({ status: "ok", env: c.env.ENVIRONMENT }));
// API routes here
app.get("/api/example", (c) => c.json({ message: "Hello" }));
// Fall through to static assets
app.all("*", async (c) => c.env.ASSETS.fetch(c.req.raw));
export default app;
workers/env.d.ts
typescript
export interface Env {
ENVIRONMENT: string;
ASSETS: Fetcher;
// Add secrets and DO bindings here
}
Package.json
Add scripts:
json
"dev:workers": "npm run build && wrangler dev", "deploy:preview": "npm run build && wrangler deploy --env preview", "deploy:production": "npm run build && wrangler deploy --env production"
Add devDependencies:
json
"@cloudflare/workers-types": "^4.20250620.0", "wrangler": "^4.42.0"
Update tsconfig.json:
json
{
"include": ["...", "workers/**/*"],
"compilerOptions": { "types": ["...", "@cloudflare/workers-types"] }
}
GitHub Actions
See references/github-actions.md for workflow templates:
- •Auto preview on PRs
- •Auto production on push to main
Durable Objects
For stateful apps (sessions, scheduled tasks, real-time), see references/durable-objects.md.
Key pattern: Use DO alarms instead of setInterval.
Setup Checklist
- •
npm install - •
npx wrangler login - •
npm run deploy:production(initial deploy) - •
npx wrangler secret put SECRET_NAME --env production - •GitHub secrets:
CLOUDFLARE_API_TOKEN,CLOUDFLARE_ACCOUNT_ID - •Custom domain: Cloudflare dashboard → Workers → Settings → Domains
Dual Deployment Pattern
Keep existing backend while adding Workers:
code
project/
├── server/ # Express/existing backend
├── workers/ # Hono/Workers backend
└── shared/ # Common code both import
├── schema.ts
├── data/
└── handlers/