Reverse Proxy
Weaver can run at a domain root or under a URL subpath. If you use a subpath, configure both Weaver and the proxy with the same base URL.
Let The Proxy Reach Weaver
Section titled “Let The Proxy Reach Weaver”Native installs listen on 127.0.0.1, which a proxy on another host can’t reach:
- Container. Nothing to do. The image listens on
0.0.0.0, so a proxy in another container or on the host reaches it through the Docker network or the published port. - Proxy on the same host as a native install. Nothing to do. The proxy connects over loopback.
- Proxy on a different host from a native install. Set Listen address in Settings → Security → Network access to
0.0.0.0, or to the interface the proxy connects over, and restart Weaver.WEAVER_HTTP_BIND_ADDRESSdoes the same from the environment.
Tell Weaver Which Proxy To Trust
Section titled “Tell Weaver Which Proxy To Trust”Without this step, Weaver sees every request as coming from the proxy. Sign-in still works, but Weaver can’t tell browsers apart, can’t see that the browser used HTTPS, and can’t match Remembered-session CIDRs against real addresses.
Add the proxy’s address, or a narrow CIDR around it, under Trusted proxy addresses or CIDRs in Settings → Security → Network access. It applies as soon as you save.
To manage it from the deployment instead, set WEAVER_TRUSTED_PROXIES, which also makes the field read-only. Separate entries with commas. A typo stops startup, so a mistyped entry is never silently skipped:
services: weaver: environment: WEAVER_TRUSTED_PROXIES: 172.20.0.5Setting the variable also makes first-run setup ask for the one-time setup code. A proxy saved in Settings doesn’t.
For requests from a trusted proxy, Weaver:
- reads the browser’s address from
X-Forwarded-For. It removes trusted hops from the right-hand end and takes the rightmost address left, which is the one your proxy recorded. A client can’t forge its way past that by adding addresses of its own on the left. - marks the session cookie
SecurewhenX-Forwarded-Protoishttps. The header must hold exactly one value,httporhttps. Anything else, including a comma-separated list, is refused with403 invalid proxy protocol header.
Forwarding headers from any other address are ignored. Trust only proxies you run, and never a Docker gateway or a whole private range. Anything that can connect from a trusted address can claim to be any browser.
Your proxy must also:
- Pass
Originthrough unchanged. A sign-in without exactly one validOriginis refused with403 a single valid Origin is required, and a session only works from the origin it signed in at. - Set
X-Forwarded-For. Without it, Weaver can’t resolve the browser’s address, and browsers behind the proxy can’t be remembered. - Send one
X-Forwarded-Protowhen it terminates TLS. - Pass
Hostthrough, or sendX-Forwarded-Host. Live updates run over a WebSocket, and Weaver refuses one whoseOrigindoesn’t match the host the request arrived at. A proxy that rewritesHostto Weaver’s own address, which nginx does by default, breaks that unless it also forwards the public name. If you can’t change the proxy, list the public name inWEAVER_HTTP_ALLOWED_HOSTSinstead.
Some proxies send the forwarding headers by default. In nginx, add them with proxy_set_header Host $host;, proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; and proxy_set_header X-Forwarded-Proto $scheme;.
Hostnames
Section titled “Hostnames”Weaver answers any hostname, so neither the public name nor a Docker service name like weaver needs to be listed.
To answer only known names, set WEAVER_HTTP_ALLOWED_HOSTS. Weaver then refuses every other name with 421 request Host is not allowed, apart from localhost and plain IP addresses. List every name that reaches Weaver, such as the Docker service name other containers use and the public name the proxy forwards:
services: weaver: environment: WEAVER_HTTP_ALLOWED_HOSTS: weaver,weaver.example.comUse hostnames only, without https:// or a path, separated by commas. An entry with a scheme, path, or wildcard stops startup, and so does an empty entry from a stray comma.
Matching is exact and ignores case. A subdomain is a different name, so weaver.example.com doesn’t cover weaver.lan.example.com. An entry with :port, such as weaver:9090, matches only that port and refuses a Host without one. A browser reaching the proxy over HTTPS sends no port, so leave the port off the public hostname unless you mean to require one.
After changing the environment, run docker compose up -d to recreate the container. Restarting the container doesn’t apply a changed environment.
Docker Subpath Example
Section titled “Docker Subpath Example”To host Weaver at a subpath like https://example.com/weaver/, add a command override:
services: weaver: image: ghcr.io/scryer-media/weaver:latest command: ["--config", "/config", "serve", "--port", "9090", "--base-url", "/weaver"] ports: - "9090:9090" volumes: - weaver-config:/config - /path/to/downloads:/downloadsThen configure your reverse proxy to forward /weaver/ to Weaver.
Good Defaults
Section titled “Good Defaults”- Preserve the
/weaverbase path end to end. - Terminate TLS at the proxy.
- Keep WebSocket support enabled if your proxy requires it explicitly.
- Keep
/graphql,/graphql/ws, assets, and app routes under the same base path. - Keep
/metricsprivate unless it is intentionally exposed to your monitoring system.
Troubleshooting
Section titled “Troubleshooting”- Missing CSS or JavaScript usually means the base URL and proxy path disagree.
- Broken live updates usually means WebSocket forwarding is missing, or the proxy rewrites
Hostwithout sendingX-Forwarded-Host. Weaver logsrefused a GraphQL socket opened from another originin that case. PassHostthrough, or list the public name inWEAVER_HTTP_ALLOWED_HOSTS. 403 a single valid Origin is requiredat sign-in means the proxy dropped or rewrote theOriginheader.403 browser verification requiredafter a successful sign-in means theOriginheader changed since sign-in, or a remembered browser now connects from an address outside Remembered-session CIDRs. Sign in again from the address you use.403 invalid proxy protocol headermeans a trusted proxy sentX-Forwarded-Protomore than once, as a list, or with a value other thanhttporhttps.- Current connection in Settings → Security → Network access shows the proxy’s address as the resolved client: the proxy isn’t under Trusted proxy addresses or CIDRs.
request Host is not allowedmeansWEAVER_HTTP_ALLOWED_HOSTSis set and doesn’t list that name. Add it or remove the variable, then recreate the container.
Related
Section titled “Related”- Security And Access explains the listen address, trusted proxies, remembered sessions, and signing in.
- Configuration lists
WEAVER_HTTP_ALLOWED_HOSTS,WEAVER_SECURE_COOKIES, andWEAVER_CORS_ALLOWED_ORIGINS. - API And Metrics covers the endpoints a proxy must forward.