Pages vs Coolify.

Two free, two excellent, two completely different jobs. With real numbers pulled from Cloudflare's docs today.

Concept 01 — Two paths, two jobs

Both free, both excellent, totally different jobs.

The question "should I use Cloudflare Pages or my Coolify VPS?" feels like a single decision, but it's really asking "what kind of thing am I deploying?" Each tool is fantastic at its own job and bad at the other's.

Option A

Cloudflare Pages

Cloudflare's global edge serves static files + tiny edge functions, with zero server to manage.

  • Built for: HTML, CSS, JS, images
  • Auto-deploys from GitHub
  • Free SSL + custom domains
  • No server, no patches, no SSH
  • Functions limited to V8 runtime (no Node, no Postgres clients)
Option B

Coolify on your VPS

Your Hetzner box running Docker. Auto-pulls from GitHub. You get a real Linux server.

  • Built for: Node, Python, Postgres, Redis, anything
  • Auto-deploys from GitHub
  • You manage the box (you already are)
  • Behind Cloudflare Access if you want
  • Single point of failure: the server
Concept 02 — The real free tier numbers

What you actually get from CF Pages, for free.

Fetched live from Cloudflare's docs. These are not estimates.

500
Builds per month
1 concurrent
20 min
Per build timeout
plenty for static sites
20k
Files per site
25 MiB each max
100
Custom domains
per project
Bandwidth
no transfer charges
100k
Function reqs/day
if you use Pages Functions
Translation

For your scale — solo dev, a handful of games + tools, even if they get a few thousand visitors — you will never hit any of these limits. The free tier is essentially "free forever" for personal projects.

Concept 03 — Where the files actually live

Pages spreads your files across the entire planet.

When you deploy to Cloudflare Pages, your built files (HTML, CSS, JS, images) get copied to Cloudflare's 330+ data centers worldwide. When a visitor in Tokyo loads your site, they get it from the Tokyo edge node, not from a single server somewhere. Latency is tiny by default.

With Coolify on your Hetzner box, every visitor talks to one machine in Germany. Fine for you and Josh. Worse for someone loading your site from Australia.

Cloudflare Pages Everywhere at once EU US JP BR AU IN Coolify on Hetzner One box in Germany Hetzner your VPS everyone talks to this one machine visitor gets nearest copy
Pages = edge-replicated. Coolify = single server.
Concept 04 — The decision rule

One question gives you the answer.

Forget the marketing. Forget the hype. The real decision is one question:

"Does my thing need a real, always-on server process?"
NO
It's HTML + CSS + JS + images, maybe a tiny serverless function for forms or auth. → Cloudflare Pages. Free, global, fast, zero maintenance. This covers 90% of personal websites, landing pages, game prototypes, dashboards that fetch from an API.
YES
It needs Postgres, Redis, a persistent Node/Python process, websockets, image processing with native libraries, or a long-running cron. → Coolify on your VPS. The server's already there, already paid for.
BOTH
This is the unlock most people miss. Frontend on Pages (fast, free, global). Backend API on Coolify (where your data lives). They talk to each other over HTTPS. Best of both worlds.
Concept 05 — Your playground specifically

What this means for your playground.

I read ~/lab/projects/playground/package.json earlier. Playground is currently a Node app with three meaningful dependencies:

Real data from your machine

Playground depends on…

better-sqlite3 pg (PostgreSQL) sharp (image processing)

All three are native Node modules — they compile against system libraries (libpq, libvips). They won't run on Cloudflare Pages' edge runtime (V8 isolates). That part of playground has to live on Coolify, period.

But the ~40 static HTML prototypes inside playground? Those are pure files. They could go on Pages individually.

So your actual options:

tts-shootout.html card-tracker.html nootropic-tracker.html server.js postgres queries

Blue = pure static, could go on Pages.
Amber = needs Node + Postgres = stays on Coolify.

My recommendation for you

Phase 1: Coolify-everything. Get all of playground deploying to Coolify first via Coolify's GitHub auto-pull. That's one deployment, one URL, one mental model. The Postgres/sqlite/sharp stuff just works.

Phase 2 (later): split the static stuff out. If you build a standalone game like duck-hunt that's pure HTML/JS, deploy that to Pages so it gets edge-replicated speed + its own URL. Best of both, only when the win is worth the extra moving part.

Bonus — both can be behind Cloudflare Access

You're already running CF Access in front of Coolify, Portainer, NocoDB, etc. The same access policies work in front of a Cloudflare Pages deployment too. Private playground, just for you and Josh? Totally doable. No extra cost.

✦ Lesson 2 recap

The model you now have…