Skip to main content
Idle Workers apps cost $0 because deployments scale to zero. This page covers the cases that cost money:
  • scale-to-zero tradeoffs
  • runaway request patterns
  • bill caps

The pricing dimensions that matter

As of 2026, the Workers Paid plan ($5/mo base) includes:
  • 10M requests/month, then $0.30 per million
  • 25B D1 reads/month, then $0.001 per million
  • 50M D1 writes/month, then $1.00 per million
  • 400k GB-s compute, then $0.02 per million
  • 1M Durable Object requests, then $0.15 per million
Things that cost nothing:
  • Idle worker (no requests)
  • Cold starts
  • Reading env vars / bindings
Things that cost money and scale with volume:
  • Every incoming HTTP request
  • Every D1 query (reads cheap, writes expensive)
  • Every DO invocation
  • WASM execution time (GB-seconds)

Patterns that exceed a free tier

Polling loops without backoff

A client that polls /api/sync/pull every 500ms sends 172,800 requests/day. With 100 such clients, that is 17M requests/day, or about $5/day. Fix: use WebSocket push (Durable Objects on Workers), or widen the polling interval with jitter. Pylon’s sync protocol supports cursor-based pulls, so clients pay only for deltas.

Loops inside a worker handler

A scheduled cron Worker triggers a function that writes to D1 in a loop. It gets rate-limited, retries the whole batch, and exceeds the D1 write quota. Fix:
  • paginate writes
  • circuit-break on retry count
  • use ctx.waitUntil for fire-and-forget work
  • measure before you ship

Durable Object hot-spotting

One room with 10k concurrent WS clients, all pinned to one DO, generates 1M+ DO requests/hour. Fix: shard rooms. On Workers, each Pylon room maps to one (sticky) Durable Object. Split a hot “global chat” room into many smaller rooms (for example, per region) to spread load across DOs instead of pinning everyone to one.

Crawlers / bots

A /api/entities/Todo route that is not gated returns 404 to bots endlessly, but each hit still costs a Worker request. Fix: use Cloudflare’s bot-fight mode and WAF rules for unauthenticated traffic on admin paths. Pylon’s router returns 401 or 403 quickly for unauthenticated non-public routes, but Cloudflare can block at the edge before the Worker even runs.

Errors in tight loops

A TypeScript function throws. The client retries immediately without backoff. Every retry costs a Worker and D1 round-trip. Fix:
  • client-side exponential backoff
  • a server-side circuit breaker for degraded paths
  • alerts on the 5xx rate rather than the request rate

Setting a budget cap

Cloudflare supports per-worker budget alerts, but not automatic cutoff. You have to write the cutoff yourself. Two patterns:
This keeps users served while you react.

Hard cap: kill switch

Bind a KV namespace BUDGET with a single key enabled: "1". At the top of your fetch handler:
A GitHub Action watches billing and turns off the flag when needed. Users see a 503 response until you re-enable it. Your bill stops growing.

Monitoring

Cloudflare’s analytics dashboard shows:
  • Request rate
  • Error rate (4xx / 5xx)
  • Subrequest count (every D1 or DO call counts)
  • Wall-clock time
Add these metrics to your own dashboard. For Pylon specifically, watch:
  • /api/sync/pull rate: anything above 10 req/sec/client is suspicious
  • /api/entities/* error rate: a 403 spike signals a policy regression, and a 5xx spike signals a bug
  • WS connection count versus rejection rate (IP cap): rejections signal an attack
  • D1 write volume versus change_log append rate: these should match

When a server is a better fit

Workers scale-to-zero does not help if:
  • You have steady traffic of 100 or more req/sec: a $25/mo AWS deploy will be cheaper
  • You need shards or long-lived game simulations: Durable Object hibernation costs add up fast
  • Your p99 latency matters and cold starts are not acceptable: a warm VPS is more predictable
  • You need Postgres (postgres-live feature): Workers supports D1 only
  • You need large file uploads: Workers has a 100 MB request cap
For those cases, see Deploy shape 2 (AWS ECS and Aurora) or Pylon Cloud.

Checklist

  1. Enable Cloudflare budget alerts the day you deploy.
  2. Add a kill switch KV namespace before problems start. It is easier to remove than to add under pressure.
  3. Client-side: always use backoff, jitter, and cursor pagination.
  4. Server-side: gate anonymous traffic at the edge, not in the Worker.