Environments
Page actions
- View as Markdown (opens in a new tab)
- Ask ChatGPT (opens in a new tab)
- Ask Claude (opens in a new tab)
ChatGPT and Claude are third-party services. The link gives them this page's public address and a short instruction. This site records nothing.
Preview: the published page may be older or missing.
Local, staging and production side by side: hosts, API platforms, data, protection and who deploys what.
https://docs.gurbanisoul.com/process/environments/
| Local | Staging | Production | |
|---|---|---|---|
| Branch | working tree | integration | main |
| Web | serve.py on :7777 | sggs-staging.vercel.app (SSO-protected; open logged in) | gurbanisoul.com (canonical) |
| API | same process | Vercel functions in the web project, one per context + all (ADR-0011) | Vercel functions in the web project: every /api path is answered by all (v1.3.10, and 1.4.0 keeps it so); each context moves to its own function, as on staging, in a later release after the app is live (Render sggs-knowledge-base.onrender.com kept as rollback) |
| iOS | simulator | TestFlight Internal | TestFlight External / App Store |
| DB profile | full | full | full (public profile until the English licence is recorded) |
| Who deploys | you | deploy-staging.yml on push to integration | deploy-production.yml on push to main |
Production domain. The canonical public host is gurbanisoul.com (apex, 200, no redirect).
www.gurbanisoul.com and the legacy Vercel alias sggs-knowledge-base.vercel.app both 308
→ apex, so there is one indexable host. DNS is Cloudflare DNS-only → Vercel; full topology and the
email routing are in docs/website/README.md.
Same-origin API (no CORS)
The browser always calls /api/* on the site’s own host, so no frontend configuration or CORS is
needed. On staging the rewrites are internal and host-conditioned: each context’s prefixes go to
its function, everything else to all. Production’s rules come after them, internal too and
host-less, so they catch every other host, including an unaliased deployment URL. production.services is empty: production (v1.3.10, and 1.4.0 after it) sends every /api path to
all. Listing the five contexts there, in a later release after the app is live, sends each
context’s prefixes to its own function in production too, and everything else (and /readyz,
/healthz) to all. Until then every path goes to all, the single API’s role on the same
database and code. The rules are generated (tools/gen_gateway.py from gateway/routes.json), for
example:
{ "source": "/api/timing(/.*)?", "has": [{ "type": "host", "value": "sggs-staging.vercel.app" }], "destination": "/api/svc/knowledge" },{ "source": "/api/timing(/.*)?", "destination": "/api/svc/knowledge" },{ "source": "/api/(.*)", "destination": "/api/svc/all" }Splitting production’s contexts out — all five in one release, after the app is live — and retiring Render afterwards are runbook: services-production.
As-code
- Deploys are CI-gated — see runbook: deploy. The platforms’ own git auto-deploys are switched off after cutover.
- Render:
sggs-knowledge-base(fromwebapp/Dockerfile) is a manually managed service; no Blueprint is committed. The site’s/apino longer reaches it, butdeploy-production.ymlkeeps deploying it every release as the API rollback target until it is retired. Staging no longer uses Render (ADR-0011). - Vercel:
frontend/vercel.json(root dir =frontend/) — production branchmain, staging a custom environment trackingintegration. deploy-verifyCI curls/api/healthand asserts/api/meta.versionmatches the branch’sAPP_VERSIONafter each deploy (catches a stale API).
Environment variables (Vercel)
| Var | Scope | Purpose |
|---|---|---|
PUBLIC_NEWSLETTER_FORM_URL | Production + Preview (unset in Development/CI/local) | Buttondown embed form endpoint for the landing’s launch-notice sign-up. Unset ⇒ the section, form and any Buttondown reference are absent from the built HTML. Public POST endpoint, not a secret, but must never be committed (NewsletterPrivacy gate). See runbook: newsletter. |
The App Store Connect API-key secrets used by TestFlight live in GitHub Environments
(production/staging), not Vercel — never echo a value; a pasted secret is a leaked secret.
Rollback
Web: Vercel Instant Rollback (automatic when the public smoke fails after promote). API: the
functions ship inside the web deployment, so a web rollback restores the previous deployment’s
functions and rewrites with it. To move the whole API back to Render, set production.api_platform
back to render with its api origin in gateway/routes.json, regenerate and release; Render keeps
deploying every release until it is retired, so this stays available until then
(runbook: services-production, step 4). Data: revert the
dataset.lock.json bump — every pinned object stays available in sggs-data. See
runbook: rollback.
Human-gated setup (one time)
Authorize the Vercel and Render GitHub Apps on the org, create the Vercel staging custom
environment + alias, add the deploy secrets to the GitHub Environments (runbook: deploy). The App Store
Connect API-key secrets live in the app repository’s environments.
Sri Guru Granth Sahib Ji — Knowledge Base wiki. Generated from commit c3d9360. Updated 13 October 2026. Verified against a661527 on 2026-09-26. This copy may be out of date; the page is at https://docs.gurbanisoul.com/process/environments/