Deployment
Vercel, one project per app, deployed from main.
Environment
Secrets live in Vercel environment variables and in /opt/ai4boards/.sanctum-ops.env
on the ops host. Never in the repository, never in chat.
The ops file is read as data by run-with-ops-env.mjs, never sourced — a
connection string contains & and ?, and sourcing one lets the shell split
the line and echo the password. That has happened once.
| Variable | Used by |
|---|---|
DATABASE_URL | app — must point at a role without BYPASSRLS |
ADMIN_DATABASE_URL | admin console only |
BEDROCK_MODEL_ID | an au. inference profile |
CRON_SECRET | user-gui, and the ops host scheduler |
STRIPE_SECRET_KEY | billing |
Scheduled work
Vercel Hobby allows two daily crons, which is not enough — the cycle tick needs
to run every five minutes. scripts/scheduler.sh runs from the ops host
instead, with TZ=Australia/Sydney set in the script: CRON_TZ in a
crontab changes when the entry fires, not the timezone the job reads.
Before believing a pricing change worked
node scripts/stripe-verify.mjs
Confirms every plan and pack points at a live Price, in AUD, GST-exclusive, at the catalogue amount, with the right interval — and that the ladder still gives better value at higher tiers. Non-zero exit, so it can gate a deploy.