Deploy to Cloudflare
You need a Cloudflare account, a zone for your domain, and Wrangler logged in (npx wrangler login).
-
Create the database and put its id into
apps/web/wrangler.jsonc, and the bucket for photos of custom exercises:Terminal window npx wrangler d1 create gymgymnpx wrangler r2 bucket create gymgym-mediaThe bucket stays private: photos are served through the Worker, to their owner only. Without the
MEDIAbinding, photo uploads are simply turned off. -
Set your domain. Change the
routespattern,BETTER_AUTH_URLandPASSKEY_RP_IDinwrangler.jsonc. -
Add secrets.
Terminal window cd apps/webnpx wrangler secret put BETTER_AUTH_SECRETnpx wrangler secret put GOOGLE_CLIENT_ID # and the other providers you wantFor Web Push reminders, generate VAPID keys with
npx @pushforge/builder vapidand setVAPID_PUBLIC_KEY,VAPID_PRIVATE_JWKandVAPID_CONTACT. -
Deploy. This builds the site, applies D1 migrations and deploys the Worker:
Terminal window corepack pnpm --filter @gymgym/web deploy -
Docs (optional).
corepack pnpm --filter @gymgym/docs deploypublishes this site as static assets.
A staging environment is defined in wrangler.jsonc with its own database; deploy it with wrangler deploy --env staging.
Photos of custom exercises
Section titled “Photos of custom exercises”People can add their own photo to an exercise they created. The browser shrinks it to 1024 px and re-encodes it, and the Worker re-parses the file and drops every EXIF, XMP and IPTC block before storing it in R2 under exercise/<id>, so no location or camera data is kept. Photos are deleted with the account, by “Reset everything” and when a backup is restored.
Exercise media
Section titled “Exercise media”Exercise images and videos aren’t included because the usual sources aren’t freely licensed. If you have licensed media, host it (for example in a public R2 bucket) and set MEDIA_BASE_URL; the app shows media only when that variable is set.