Install and configureReverse proxy

Reverse proxy and HTTPS

Put SlugBase behind nginx, Caddy, or Traefik: set public URLs, preserve client IP, and keep cookies working.

What you need

  • A domain name and TLS certificate (Let’s Encrypt or your CA).
  • A reverse proxy that can forward HTTP to the SlugBase container or process (default upstream port 5000).
  • Environment variables BASE_URL and FRONTEND_URL set to the public HTTPS URL users type in the browser.

SlugBase trusts one proxy hop, so it correctly reads the client's real IP and protocol from the headers your proxy sends. Session cookies are automatically marked Secure when NODE_ENV=production and BASE_URL starts with https://.

If BASE_URL stays http:// while users reach the site over HTTPS, secure cookies may not match how browsers treat the session. Set both BASE_URL and FRONTEND_URL to the canonical https:// origin.

Steps

Point DNS at your proxy

Create an A/AAAA (or CNAME) record for your hostname to the machine or load balancer that terminates TLS.

Forward to SlugBase

Proxy / to the backend listening on PORT (default 5000). Use HTTP to the upstream unless you terminate TLS again behind the proxy.

Typical headers to set (names may vary by proxy):

  • Host — original host from the client.
  • X-Forwarded-Protohttps when the client used HTTPS.
  • X-Forwarded-For — client IP chain.

Align environment variables

Set:

NODE_ENV=production
BASE_URL=https://bookmarks.example.com
FRONTEND_URL=https://bookmarks.example.com

Add CORS_EXTRA_ORIGINS only if a separate origin loads the SPA or calls the API. See Configuration.

Reload and test

Open the public URL, complete or confirm login, and verify Admin and Bookmarks load without mixed-content or redirect loops.

Example snippets

bookmarks.example.com {
  reverse_proxy localhost:5000
}

Verify

  • Open https://your-domain/api/health and confirm you get a successful response.
  • Sign in and refresh the page — you should stay signed in.
  • If OIDC login is configured, complete a full login cycle to confirm the callback URL works correctly.

Troubleshooting