Skip to main content
By default, each deployed app is served on your organization’s provisioned domain as two hosts:
  • App (frontend): your-app.apps.yourcompany.com
  • API: your-app.api.apps.yourcompany.com
Vanity URLs let you serve a specific app on a domain you own — e.g. console.mycompany.com — by placing your own reverse proxy in front of the app’s existing hosts. The deployment itself doesn’t change: you tell the app which public URLs to advertise, and your proxy routes your domain to the internal hosts.
Vanity URLs use a bring-your-own reverse proxy model. You keep control of DNS, TLS, and routing for your domain; Synthetiq just makes the app emit the right public URLs (OAuth issuer, redirects, cookies, API base). There’s no change to how the app is built or deployed.

How it works

On its internal hosts the app serves two roots: the frontend on the app host, and the API + OAuth on the API host. The API host serves your app’s data API under /api plus the OAuth/OIDC surface at /oauth, /auth, /.well-known, and /mcp. Your proxy maps your public domain onto those.

Configure the app’s public URLs

Set two values on the production app:
The simplest setup is one domain with a path for the API: app_url = https://console.mycompany.com and api_url = https://console.mycompany.com/gateway. Your proxy then needs a single rule. You can also use a dedicated API subdomain (api_url = https://api.console.mycompany.com) if you prefer — see the tip at the end of the Cloudflare example.
/gateway is an arbitrary routing prefix — name it anything (/backend, /edge, …). Just avoid the app’s own top-level paths (/api, /oauth, /auth, /.well-known, /mcp); /api would produce awkward …/api/api/… URLs.
Set them from the desktop app — open the app → DeploymentsDomain tab → Custom domain, enter the App URL and API URL, save, then redeploy — or from the CLI:
Clear a vanity URL by passing an empty string: --app-url "".
A vanity URL only takes effect after a redeploy — the app’s API base is baked at build time. Once it’s live, the app is served only from your domain: the default your-app.apps.yourcompany.com URL stops working, because the app now advertises your domain for login, cookies, and API calls.

What your reverse proxy must do

Your proxy sits in front of your domain and forwards to the app’s internal hosts, rewriting the Host header so Synthetiq’s edge routes to the right app.
1

Terminate TLS for your domain

Serve console.mycompany.com with your own certificate.
2

Route the API base to the internal API host

Send everything under api_url to your-app.api.apps.yourcompany.com, with Host rewritten and the api_url path prefix (e.g. /gateway) stripped. The app mounts /api (data), /oauth, /auth, /.well-known, and /mcp beneath api_url — all of these must reach the API host.
3

Route everything else to the internal frontend host

Send all other paths to your-app.apps.yourcompany.com (the static frontend), with Host rewritten.
The internal hostnames are your app’s default URLs — the Production URL shown in the Domain tab (your-app.apps.yourcompany.com) and its API counterpart (your-app.api.apps.yourcompany.com).

Example: Cloudflare

This example serves console.mycompany.com, with the API under /gateway, using a Cloudflare Worker for the routing.
1

Add the domain to Cloudflare

Add a proxied (orange-cloud) DNS record for console.mycompany.com. The Worker (next step) intercepts every request and connects to Synthetiq’s hosts itself, so this record’s target is never used as an origin — it exists only so the hostname resolves through Cloudflare (which runs the Worker and terminates TLS). Use a placeholder target: an AAAA record pointing to 100:: (or an A record to 192.0.2.1), with Proxy status: Proxied. Grey-cloud (DNS-only) will not work. Cloudflare provisions TLS automatically.
2

Deploy the Worker

Create a Worker with the routing below and bind it to the route console.mycompany.com/*. Replace the two origin hostnames with your app’s defaults.
3

Set the URLs and redeploy

Set app_url / api_url on the app (above) and redeploy. Then sign in at https://console.mycompany.com to confirm the login round-trip works end to end.
Prefer a dedicated API subdomain? Set api_url = https://api.console.mycompany.com, point that subdomain at the API origin (Host rewritten, no path to strip), and point console.mycompany.com at the frontend origin. Same idea, two hostnames instead of one Worker.

CORS

With the path layout (api_url = https://console.mycompany.com/gateway) the frontend and API share one origin, so there is no CORS to think about. With the subdomain layout (api_url = https://api.console.mycompany.com) the frontend and API are different origins, so requests are cross-origin — but this is handled automatically, the same way the default two-host deployment already is (its frontend and API also live on different hosts). The app allows browser requests whose Origin matches app_url. So it just works, provided:
  • You set both app_url and api_url — CORS is keyed to app_url (the frontend origin). Setting only api_url leaves the app allowing the default host, and your frontend’s calls would be rejected.
  • Your proxy forwards the Origin header unchanged and passes OPTIONS preflight requests through to the API host (standard proxy behavior).
Cross-origin API calls authenticate with Bearer tokens rather than cookies, so there’s nothing extra to configure for credentials.

Notes and limitations

  • Redeploy required. Setting or changing a vanity URL only takes effect on the next deploy.
  • Use your vanity URL once it’s live. The app then advertises only your domain for login and API calls, so opening the default your-app.apps.yourcompany.com URL won’t work as an entry point — its API calls are rejected (CORS) and its login won’t complete. The internal hosts do stay network-reachable behind Synthetiq’s edge (that’s how your proxy reaches them); to restrict them to proxy-only access, ask us about origin hardening.