[HELP] [forward-auth] Authelia Zoraxy Forward-Auth - configuration issue
Hello everyone,
unfortunately, I'm having some difficulties configuring forward-auth.
Zoraxy runs natively on a Linux server. I host a test website (test1.mydomin.com) in a nginx docker container. Authelia (auth.mydomain.com) is running in another container.
I would like to configure Zoraxy so that the test website (test1.mydomin.com) is protected with forward-auth and I get the Authelia password entry dialog before I can access the test website.
My problem is that the test website is displayed without requiring a password, even though I have activated forwad_auth.
Describe the networking setup you are using
- Are you using the docker build of Zoraxy? no
- Your Zoraxy version? v3.2.5r2
- Are you using Cloudflare? no
- Are your system hosted under a NAT router? no
This is my configuration:
Configuration settings for the Forward Auth provider:
Authentication Provider for test1.mydomin.com:
Zoraxy log:
Authelia log:
@Settings for the Forward Auth provider: Can anyone tell me which headers should be specified here?
Thank you very much.
How can I add the “forward-auth” tag? I can not select the appropriate lable.
Hi @teomemora
How can I add the “forward-auth” tag?
That tag can only be added by me, it is kinda like a issue class category that I will assign onto an incoming issue and see which section of code might be the problem.
Btw, you might also want to tag the forward-auth module owner in the README if you still cant figure out how the set it up correctly in a week or two. From what I see from these type of issues, it is mostly related to networking / routing in your particular network environment. If you eventually figure out the reason, please feel free to share it here or on the wiki, have a nice day!
Thank you for your feedback.
I will report back as soon as a solution has been found.
You are probably right, and it is just a routing or network problem. It is also possible that some necessary headers are missing.
To narrow down the problem further:
-
A gitea docker instance is also running on the same server. I have configured oauth2 here so that I can log in to gitea with my authelie user. That works.
-
Even when I call up the domain: ‘auth.mydomain.com’, I can log in to authelia.
Only the forward-auth access protection no longer works since the change from zoraxy v3.1.9 to 3.2.5r2.
-
Even a fresh installation of zraxy 3.2.5r2 without old config data did not help me.
-
Forward-auth works in version 3.1.9.
I also looked at the code and found that zoraxy v3.1.9 sends a POST request and zoraxy v3.2.5r2 always sends a GET request to the authelia server (auth.mydomain.com).
zoraxy 3.1.9
zoraxy-3.1.9\src\mod\auth\sso\authelia\authelia.go -> HandleAutheliaAuth:103
req, err := http.NewRequest("POST", autheliaBaseURL+"/api/verify", nil)
zorazy 3.2.5r2
zoraxy-3.2.5r2\src\mod\auth\sso\forward\forward.go -> HandleAuthProviderRouting:164
req, err := http.NewRequest(http.MethodGet, ar.options.Address, nil)
But that can't really be the cause of the problem, can it?
@james-d-elliott I would be grateful if one of the authelia experts could help.
Best regards.
The X-Forwarded-* headers are being overwritten by a proxy. If you're reverse proxying Authelia via Zoraxy you should be using the same scheme part and host part of the URL in the forward auth address as the proxy to settings, not the proxy from settings.
The method used is not relevant here, the POST method was actually an incorrect implementation.
I'm adding a switch to use X-Original-Method and X-Original-URL again, but Authelia is not providing future support for the /api/verify endpoint and neither should Zoraxy try to. This endpoint is unnecessarily complicated and will not receive any feature additions or bug fixes outside of security fixes, and we'll never cater any documentation to its use.
Thank you for your feedback james-d-elliott
It works! :-)
That was exactly the problem. It was mainly because the address was incomplete.
I am now using the following settings:
In my own words, I would say that Zoraxy must be able to reach the internal address of the Authelia server.
So for someone who has not set up an extra SSL certificate for internal communication between Zoraxy and the Authelia Docker container, the address should then be as follows:
http://your-own-domain.com:exposed-port/api/authz/forward-auth
The Authelia configuration.yml should also be configured accordingly:
...
session:
secret: '__SECRET__'
cookies:
- name: 'authelia_session'
domain: 'your-own-domain.com'
authelia_url: 'https://auth.your-own-domain.com'
expiration: '1 hour'
inactivity: '5 minutes'
...
@tobychui & @james-d-elliott Thank you again for your help and your excellent and diligent development work! :muscle:
@teomemora
I am also trying to setup authelia with Zoraxy. Since you managed to get it running, would you mind to provide more details how you managed to do it?
I am already strugling with configuring the relevant proxy paramters to get to Auth logging page. Help would really be appeciated!
The effective solution is to make sure that the configuration of the forward auth section uses a URI that doesn't get proxied. So for example if you have Zoraxy on a docker network with Authelia, and Authelia's container name is set to authelia, you'd use http://authelia:9091/api/authz/forward-auth, similar to how you'd configure the reverse proxy element.
There's a new version I think which includes an option to toggle the X-Original-* headers, which could be used with most proxies. The cause of the issue is a proxy changing the header before it's transported to Authelia, so if the proxy doesn't set this header you're good to go. The URI to use for X-Original-* is https://<domain>/api/authz/auth-request. This option has not been as tested as the other so far so YMMV.
Hi @james-d-elliott,
currently I have Zoraxy running on an LXC and Authelia in a Docker LXC, both on the same Proxmox host.
(I also have a working installation with NPM (Proxmox LXC) as my proxy, setup with the NGINX snippets from the Authelia Integration guide but wanted to test Zoraxy since it seems to be more modern and better maintained.)
More info about my setup can also be found here where I reported a bug: https://github.com/tobychui/zoraxy/issues/816#issue-3403201431
Concerning Zoraxy...
These are my auth.mydomain.com proxy settings:
I tried to set this up similar to what is setup in NPM considering the includes from the NGINX snippets. What I am not sure about are the variables. Can I use the same as for NPM?
Forward auth is setup like this:
Any issues you see with these settings? Do I need to change anything in the docker compose.yml to make it work with Zoraxy or should it work with the same settings since it is working with NPM? Do I need to make any adjustments to the docker compose.yml of Zoraxy? (it's very basic only)
services:
zoraxy:
image: zoraxydocker/zoraxy:latest
container_name: zoraxy
restart: unless-stopped
ports:
- 80:80/tcp
- 443:443/tcp
- 8001:8000/tcp
- 8001:8000/udp
volumes:
- ~/docker/zoraxy/config/:/opt/zoraxy/config/
- ~/docker/zoraxy/plugin/:/opt/zoraxy/plugin/
- /var/run/docker.sock:/var/run/docker.sock
- /etc/localtime:/etc/localtime:ro
extra_hosts:
- "host.docker.internal:host-gateway"
environment:
FASTGEOIP: "false"
Here for the complete auth.mydomain.com.conf:
{
"ProxyType": 1,
"RootOrMatchingDomain": "auth.mydomain.com",
"MatchingDomainAlias": [],
"ActiveOrigins": [
{
"OriginIpOrDomain": "192.168.188.56:9091",
"RequireTLS": true,
"SkipCertValidations": true,
"SkipWebSocketOriginCheck": true,
"Weight": 1,
"MaxConn": 0,
"RespTimeout": 0
}
],
"InactiveOrigins": [],
"UseStickySession": false,
"UseActiveLoadBalance": false,
"Disabled": false,
"BypassGlobalTLS": false,
"TlsOptions": {
"DisableSNI": false,
"DisableLegacyCertificateMatching": false,
"EnableAutoHTTPS": false,
"PreferredCertificate": {}
},
"VirtualDirectories": [],
"HeaderRewriteRules": {
"UserDefinedHeaders": [
{
"Direction": 0,
"Key": "Host",
"Value": "$host",
"IsRemove": false
},
{
"Direction": 0,
"Key": "X-Original-URL",
"Value": "$scheme://$http_host$request_uri",
"IsRemove": false
},
{
"Direction": 0,
"Key": "X-Forwarded-Proto",
"Value": "$scheme",
"IsRemove": false
},
{
"Direction": 0,
"Key": "X-Forwarded-Host",
"Value": "$http_host",
"IsRemove": false
},
{
"Direction": 0,
"Key": "X-Forwarded-URI",
"Value": "$request_uri",
"IsRemove": false
},
{
"Direction": 0,
"Key": "X-Forwarded-Ssl",
"Value": "on",
"IsRemove": false
},
{
"Direction": 0,
"Key": "X-Forwarded-For",
"Value": "$remote_addr",
"IsRemove": false
},
{
"Direction": 0,
"Key": "X-Real-IP",
"Value": "$remote_addr",
"IsRemove": false
}
],
"RequestHostOverwrite": "",
"HSTSMaxAge": 0,
"EnablePermissionPolicyHeader": false,
"PermissionPolicy": {
"accelerometer": [
"*"
],
"ambient_light_sensor": [
"*"
],
"autoplay": [
"*"
],
"battery": [
"*"
],
"camera": [
"*"
],
"cross_origin_isolated": [
"*"
],
"display_capture": [
"*"
],
"document_domain": [
"*"
],
"encrypted_media": [
"*"
],
"execution_while_not_rendered": [
"*"
],
"execution_while_out_of_viewport": [
"*"
],
"fullscreen": [
"*"
],
"geolocation": [
"*"
],
"gyroscope": [
"*"
],
"keyboard_map": [
"*"
],
"magnetometer": [
"*"
],
"microphone": [
"*"
],
"midi": [
"*"
],
"navigation_override": [
"*"
],
"payment": [
"*"
],
"picture_in_picture": [
"*"
],
"publickey_credentials_get": [
"*"
],
"screen_wake_lock": [
"*"
],
"sync_xhr": [
"*"
],
"usb": [
"*"
],
"web_share": [
"*"
],
"xr_spatial_tracking": [
"*"
],
"clipboard_read": [
"*"
],
"clipboard_write": [
"*"
],
"gamepad": [
"*"
],
"speaker_selection": [
"*"
],
"conversion_measurement": [
"*"
],
"focus_without_user_activation": [
"*"
],
"hid": [
"*"
],
"idle_detection": [
"*"
],
"interest_cohort": [
"*"
],
"serial": [
"*"
],
"sync_script": [
"*"
],
"trust_token_redemption": [
"*"
],
"unload": [
"*"
],
"window_placement": [
"*"
],
"vertical_scroll": [
"*"
]
},
"DisableHopByHopHeaderRemoval": false
},
"EnableWebsocketCustomHeaders": false,
"AuthenticationProvider": {
"AuthMethod": 0,
"BasicAuthCredentials": [],
"BasicAuthExceptionRules": [],
"BasicAuthGroupIDs": null,
"ForwardAuthURL": "",
"ForwardAuthResponseHeaders": null,
"ForwardAuthResponseClientHeaders": null,
"ForwardAuthRequestHeaders": null,
"ForwardAuthRequestExcludedCookies": null
},
"RequireRateLimit": false,
"RateLimit": 0,
"DisableUptimeMonitor": false,
"DisableChunkedTransferEncoding": true,
"AccessFilterUUID": "default",
"DefaultSiteOption": 0,
"DefaultSiteValue": "",
"Tags": [
"Network"
]
}
For completeness sake here also my authelia configuration.yml:
theme: dark
server.address: tcp://0.0.0.0:9091
log:
level: warn
file_path: /etc/authelia/authelia.log
totp:
issuer: mydomain.com
period: 30
skew: 1
authentication_backend:
file:
path: /etc/authelia/users.yml
watch: true
access_control:
default_policy: one_factor
rules:
- domain:
- "auth.mydomain.com"
policy: bypass
- domain: # Proxies only requiring username and password
- "glance.mydomain.com"
- "proxmox.mydomain.com"
policy: one_factor
session:
name: authelia_session
secret: <snipped>
same_site: lax
inactivity: 5m
expiration: 1h
remember_me: 1M
cookies:
- domain: mydomain.com
authelia_url: https://auth.mydomain.com
regulation:
max_retries: 5
find_time: 2m
ban_time: 10m
storage:
encryption_key: <snipped>
local:
path: /etc/authelia/db.sqlite
identity_validation:
reset_password:
jwt_secret: <snipped>
jwt_lifespan: 5 minutes
jwt_algorithm: HS256
notifier:
filesystem:
filename: /etc/authelia/emails.txt
Set it to http://192.168.188.56:9091/api/authz/forward-auth.
hi @FirebladeBMW
Hello,
I can't say for sure if this is the problem, but I noticed the following in your configuration:
You have enabled TSL in Zorax for internal communication with your authelia server (auth.mydomain.com / 192.168.88.188.56:9091).
However, there is no TLS entry in your authelia configuration.yml. This means that the authelia server only speaks http.
-
I would suggest that you either specify the TLS certificate in the authelia configuration.yml (https://www.authelia.com/configuration/miscellaneous/server)
-
or uncheck “Require TLS” and “Skip Verification” in the Zoraxy upstream configuration
That might help.
Best regards
Thank you both for your feedback! Really appreciated!
At least Zoraxy now is forwarding the request to Authelia. Login page of Authelia is loading but spinner logo keeps "spinning" and not loading the login part of the site with a red error message (banner)
It seems he is missing the X-Original-URL header.
Here is the error log from Authelia for this login session:
time="2025-09-11T19:59:37+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/ (method GET)."
time="2025-09-11T19:59:37+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/static/css/index.CRV7Mtik.css (method GET)."
time="2025-09-11T19:59:37+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/static/js/index.BTAcfhmB.js (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/locales/en/consent.json (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/locales/de/consent.json (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/locales/en/portal.json (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/locales/en/settings.json (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/locales/de/portal.json (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/locales/de/settings.json (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/favicon.ico (method GET)."
time="2025-09-11T19:59:38+02:00" level=debug msg="Check authorization of subject username= groups= ip=192.168.188.101 and object https://auth.mydomain.com/api/state (method GET)."
time="2025-09-11T19:59:38+02:00" level=error msg="Error occurred retrieving user session" error="unable to retrieve session cookie domain: failed to parse X-Original-URL header: parse \"://$http_host/api/state\": missing protocol scheme" method=GET path=/api/state remote_ip=192.168.188.165 stack="github.com/authelia/authelia/v4/internal/handlers/handler_state.go:15 StateGET\ngithub.com/authelia/authelia/v4/internal/middlewares/bridge.go:66 handlerMain.(*BridgeBuilder).Build.func7.1\ngithub.com/authelia/authelia/v4/internal/middlewares/headers.go:65 SecurityHeadersCSPNone.func1\ngithub.com/authelia/authelia/v4/internal/middlewares/headers.go:105 SecurityHeadersNoStore.func1\ngithub.com/authelia/authelia/v4/internal/middlewares/headers.go:30 SecurityHeadersBase.func1\ngithub.com/fasthttp/[email protected]/router.go:441 (*Router).Handler\ngithub.com/authelia/authelia/v4/internal/middlewares/log_request.go:14 handlerMain.LogRequest.func30\ngithub.com/authelia/authelia/v4/internal/middlewares/errors.go:38 RecoverPanic.func1\ngithub.com/valyala/[email protected]/server.go:2455 (*Server).serveConn\ngithub.com/valyala/[email protected]/workerpool.go:225 (*workerPool).workerFunc\ngithub.com/valyala/[email protected]/workerpool.go:197 (*workerPool).getCh.func1\nruntime/asm_amd64.s:1693 goexit"
Wireshark:
Alright, I think I found the issue...
The custom headers do not accept multiple values. It will only parse the last variable. (no matter if separated by "," or not)
Here, I entered for X-Original-URL " $scheme://$host$request_uri " (also tried $scheme**,://,$host,**$request_uri)
This will result in X-Original-URL ommitting the first 2 variables and only parsing the entered chars + last variable:
When I try to trick this by just entering " $host " I can get to the login window and log in. However, it will not move on to the Authelia confirmation window, where it confirms that you are logged in. It will just reload the Login window and you can log in again...
When opening another page than than the Auth itself it will let you progress to the actual page. But well, by doing this you will lose the URI part of the URL.
I am using v3.5.2r2 currently. It's a bug I assume?
I'm pretty sure you can remove the custom headers and it'll work, doesn't seem like a forward auth issue. All of my testing has been with the default header configuration in Zoraxy.
Yes, just got it working now. Also tested then with removing as many headers as possible to see what is the minimum requirement. And yes, you are right. I can confirm, none is needed... 🤣🤦♂️
Really was going crazy with this... Flushed all caches, rebooted the whole network etc... Headers not accepting multiple values still is a bug though?
Anyways, thank you very much, both of you! Truely appreciated!!!
Now I have to find out how to get my OPNsense working with Zoraxy! That's the only site I cannot access via reverse proxy. but with IP only.