Files
touchbase/docs/progress/2026-05-03-ci-and-polish.md
2026-05-05 10:39:59 -04:00

4.7 KiB

2026-05-03 — CI + Reminder Lead Configurability

Companion to BuildLog.md. Predecessor: 2026-05-03-production-prep.md.

Milestone

CI workflow at .github/workflows/ci.yml runs on every push/PR — lint, typecheck, tests against a real Postgres service container, plus a parallel docker-build job that exercises the Dockerfile. Reminder lead time is now env-configurable via REMINDER_LEAD_MIN (defaults to 1440 = 24h).

What landed

Path Role
.github/workflows/ci.yml Two jobs: test (Postgres 16 service container with btree_gist + pgcrypto, prisma generate, prisma migrate deploy, lint, tsc, test) and docker (buildx with GHA cache, builds the runtime image without pushing). Concurrency-cancelled on superseded refs.
src/lib/reminders.ts REMINDER_LEAD_MS constant replaced with reminderLeadMs() reading REMINDER_LEAD_MIN env (default 1440). Set on both web and worker so producer-side scheduling and handler agree.
.env.example Added REMINDER_LEAD_MIN=1440 example.
docs/deploy.md Documented REMINDER_LEAD_MIN in the optional env-vars table.

What's verified

  • pnpm test92/92 green
  • pnpm lint — clean
  • pnpm exec tsc --noEmit — clean
  • CI workflow YAML is syntactically valid (Next.js / pnpm versions match repo). Live verification awaits a push to GitHub.

Decisions ratified

Decision Resolution
CI runner ubuntu-latest. Standard, fast, free for public repos and reasonable for private.
Postgres in CI Service container postgres:16 (matches our prod image), btree_gist + pgcrypto installed via a psql step.
Test DB strategy in CI One DB (touchbase_test); migrations applied via prisma migrate deploy; tests run against the same connection. Reason: simplest possible setup. Per-test parallel DBs is overkill at our test count.
Docker job Builds the image but doesn't push. Reason: no registry yet. Push gets added when we have a release process.
Cache strategy pnpm action caches the store via Node setup; docker/build-push-action uses GHA cache backend. Reason: keeps CI under 2 min on warm cache.
Concurrency Superseded runs cancelled on the same ref. Reason: avoid wasting CI minutes on stale commits.
REMINDER_LEAD_MIN default 1440 (24h) — same as the previous hardcoded value. Reason: behavior unchanged absent override.
REMINDER_LEAD_MIN validation Falls back to 1440 if env value is invalid (NaN, negative, missing). Reason: don't crash on a typo; do something reasonable.
Where to set REMINDER_LEAD_MIN Both web tier (producer) AND worker (handler reads via the same module). Documented in deploy.md.

Gotchas hit

None.

Open questions

  1. Customer-visible brand name (still pending)
  2. Currency
  3. Stripe account ownership
  4. Real domain + Caddy config
  5. Image registry choice (still deferred)
  6. NEW: When should CI start running — push to GitHub now, or wait until you cut a v1 branch? Doesn't affect code; just operational.

Roadmap status

  • v1 feature-complete
  • Production prep done
  • CI done 2026-05-03 (this session)
  • Reminder lead time now configurable

Outstanding gates before opening to real customers (operational, not code):

  1. Live Stripe verification in test mode (when keys arrive)
  2. Brand + policy decisions
  3. First production deploy

The remaining code-track polish items are all genuinely optional:

  • Sentry / GlitchTip integration for production error tracking. Half-day, more if we want sourcemaps uploaded by CI. Useful once we're live; not before.
  • CSP / security headers via Next config or Caddy. Half-day. Worth doing before opening to real customers.
  • Rate limiting on /api/auth/* and the booking endpoint. We currently rely on Postgres exclusion constraints to prevent double-booking races, but a determined caller could spam magic-link emails (Resend has its own quota, but still). Half-day to wire @upstash/ratelimit or a simple in-memory limiter.
  • Audit logging for admin actions. We have an AuditLog table from §4 of BuildLog.md but no calls to it. Half-day to wire into the admin CRUD actions.

My pick if continuing: rate limiting (concrete safety win) or audit logging (load-bearing for any compliance conversation later). Sentry is high-value but easier to add post-launch when we know what kinds of errors occur.

If pausing: this is a clean stopping point.

How to resume

cd /Users/noise/Documents/code/touchbase
pnpm test                    # 92/92
pnpm lint                    # clean
pnpm exec tsc --noEmit       # clean

# CI will run on push:
git push origin main         # then check Actions tab on GitHub