That’s fabulous news! I just checked my Client Certificates and all 4 of my hosts are listed.
Hello, a security question that I don’t understand… I have the tunnel set up with Cloudflare and from outside I can access my home assistant fine with https://xxxx but from within the network I have to access via ip or http://local.name:8123 What am I wrong about? I would be interested if it also worked with a certificate from within. Thank you
Something with your internal routing and DNS; I can access my external URL from inside my network just fine.
True, it doesn’t fix Google Assistant. I ended up creating a separate endpoint with limited access to the token and api endpoints required for GA, only allowed access to that using a service token, and created an overly complex Cloudflare worker which checks incoming connections. It doesn’t add much security, but at least it’s another layer…
May not help but I also got IOS app working alongside web UI with CF Access and JumpCloud (Insert any IDP here).
Tested using two approaches:
Approach 1 was Client → CF Access → HA Proxy (Parse JWT and set validated email to X-Auth-Header) → Header Auth to Home Assistant
Approach 2 was Client → CF Access → Cloudflared Tunnel → HomeAssistant Header Auth using cf-access-authenticated-user-email header.
Approach 2 is far less moving parts - and because you are using a Clouflared Warp Tunnel which is secured privately, there is no need to validate the JWT because the cf-authenticated header can be trusted.
To get the IOS app to work was a little painful, annoying but you can exclude /api from cf access and then it works fine. Unfortunately reduces the level of reverse proxy protection but still better than having the whole lot exposed. When custom headers are supported in the IOS or Android App service tokens will be able to secure the API endpoint.
Stating the obvious - if you go with either option, you need to ensure you either parse the JWT correctly or you only allow cloudflared, mutual TLS to validate the cf-authenticated email header came from cf correctly. Otherwise you can just send the header to HA if your implementation is on the internet via other means it may be accessible with a forged header.
I have remote access to my HomeAssistant with Clouflare tunnel. Is there a way to use authenticator app on iphone to open the tunnel (like LastPassAuthenticator)?
Reason I ask is that companion app on iPhone does not work (or at least I have not managed to get it to work) with 2FA using email or Google…
I think I missed something but I can’t find what.
I configured the CF Tunnel via docker-compose
:
homeassistant:
container_name: homeassistant
image: "ghcr.io/home-assistant/home-assistant:stable"
volumes:
- ./homeassistant/config:/config
- /etc/localtime:/etc/localtime:ro
- /run/dbus:/run/dbus:ro
restart: unless-stopped
env_file:
- shared.env
devices:
- /dev/ttyACM0:/dev/ttyACM0
privileged: true
network_mode: host
tunnel:
container_name: cloudflared-tunnel
image: cloudflare/cloudflared
restart: unless-stopped
env_file:
- shared.env
command: tunnel run
environment:
- TUNNEL_TOKEN=${TUNNEL_TOKEN}
network_mode: host
It is running and I see it connected well:
Logs:
cloudflared-tunnel | 2024-04-09T17:06:18Z INF Updated to new configuration config="{\"ingress\":[{\"hostname\":\"<masked-hostname>\",\"originRequest\":{},\"service\":\"http://localhost:8123\"},{\"service\":\"http_status:404\"}],\"warp-routing\":{\"enabled\":false}}" version=11
When I’m connecting to that hostname, I need to verify my email.
But after verifying I get Bad Gateway 502 from Cloudflare.
The log in the tunnel client is:
cloudflared-tunnel | 2024-04-09T17:24:44Z ERR error="Unable to reach the origin service. The service may be down or it may not be responding to traffic from cloudflared: dial tcp 127.0.0.1:8123: connect: connection refused" connIndex=1 event=1 ingressRule=0 originService=http://localhost:8123
cloudflared-tunnel | 2024-04-09T17:24:44Z ERR Request failed error="Unable to reach the origin service. The service may be down or it may not be responding to traffic from cloudflared: dial tcp 127.0.0.1:8123: connect: connection refused" connIndex=1 dest=https://<masked-hostname>/ event=0 ip=198.41.200.23 type=http
cloudflared-tunnel | 2024-04-09T17:24:44Z ERR error="Unable to reach the origin service. The service may be down or it may not be responding to traffic from cloudflared: dial tcp 127.0.0.1:8123: connect: connection refused" connIndex=1 event=1 ingressRule=0 originService=http://localhost:8123
cloudflared-tunnel | 2024-04-09T17:24:44Z ERR Request failed error="Unable to reach the origin service. The service may be down or it may not be responding to traffic from cloudflared: dial tcp 127.0.0.1:8123: connect: connection refused" connIndex=1 dest=https://<masked-hostname>/favicon.ico event=0 ip=198.41.200.23 type=http
My HomeAssistant is accessible at the same time from the internal IP, and from inside the docker-compose machine I can curl localhost:8123
and get the right HTML.
The configuration.yml
includes the next part:
http:
use_x_forwarded_for: true
trusted_proxies:
- 172.30.33.0/24
And of course, I restarted the docker-compose
many times.
(Do you need any more info?)
Update:
Ok, first I found that even with the installed tunnel connector, I need to configure in the Tunnel settings the local IP address (192.168.1.23) instead of the localhost.
Second, I need to check which addresses are accessing to the HA and allow them in the proxy config.
I get a “Cannot reach [test] myapp” error if I put the access rules in place when linking. If I remove the access rules, I am able to link Google Assistant. are the access rules supposed to be activated after the first link has been established?
I couldn’t connect with cast dashboard. You may need to include websocket in the rule: /api/websocket
This works for me:
(http.host eq “my.homeassistant.com” and not cf.tls_client_auth.cert_verified and http.request.uri.path eq “/api/websocket/”)
It’s probably an header issue.
God luck!
Hello
One short question how , If it is possible, set an aditiona host
additional_hosts:
- hostname: router.example.com
service: http://192.168.1.1
But my sevice i Want to point to a diferent homeassitant instantnce in a diferent location, so it’s not o the same network.
It is posibel to resolve it.
Hi All
Just thought I would post that I have had success with accessing the HA app without getting the Cloudfare ‘forbidden’ message while outside of the network, and also without breaking google home.
Unsure if this is the right way of going about it but adding another tunnel hostname in Cloudfare pointed at the same domain but adding a subdomain worked a treat.
To explain further:
- Following the instructions above I managed to get google assistant working and local access to the HA instance. However attempting to externally access at https://xxxxxxxx.net through the HA app I could not get past the Cloudfare ‘Forbidden’ or the email authentication screen.
- In Cloudfare under the existing tunnel created as documented, under Public Hostname, I added another hostname with subdomain, https://house.xxxxxxxx.net
- Pointing the HA app external URL to this new hostname allows access without trouble, and, testing Google Home functionality everything is visible and online.
If this looks incorrect and I have rendered my instance unsafe in any way please let me know and I will go back to choosing which function to stop using, otherwise I hope this helps someone else.
The intent is to allow secure access over CF tunnels, but you’re exposing your HA to the internet directly via that new hostname. When HA has a remote compromise (and everything has one sooner or later) you’ll be wide open. I suggest adding authentication instead via github, google, etc.
Note this will not make the mobile app work; there’s a hacky workaround with certs on android but not aware of anything on iOS. I don’t care about this myself as I’m always VPN’d to my home LAN anyway.
Hoping someone can assist, I can’t get header auth to work through cloudflare anymore.
A little bit about my setup is I use cloudflared and cloudflare access. I validate the user from cloudflare access using their header.
username_header: Cf-Access-Authenticated-User-Email
So if I set the header in the browser and browse locally it works and I see the header in the debug log.
2024-06-12 22:32:35.069 DEBUG (MainThread) [custom_components.auth_header] <CIMultiDictProxy('Host': 'home.net.xxxx.nz', 'Connection': 'keep-alive', 'Content-Length': '131', 'sec-ch-ua': '"Google Chrome";v="125", "Chromium";v="125", "Not.A/Brand";v="24"', 'sec-ch-ua-platform': '"macOS"', 'sec-ch-ua-mobile': '?0', 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/125.0.0.0 Safari/537.36', 'Content-Type': 'text/plain;charset=UTF-8', 'Accept': '*/*', 'cf-access-authenticated-user-email': '[email protected]',
2024-06-12 22:32:35.069 DEBUG (MainThread) [custom_components.auth_header] Got actual IP 192.168.2.197
However when I connect through Cloudflare Access it errors with “unable to connect to homeassistant”
Log says: " Login attempt failed
Login attempt or request with invalid authentication from xyz"
However - the relevant header is there…
2024-06-12 22:34:12.207 DEBUG (MainThread) [custom_components.auth_header] <CIMultiDictProxy('Host': 'ha.xxxx.xy', 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/125.0.0.0 Safari/537.36', 'Content-Length': '127', 'Accept': '*/*', 'Accept-Encoding': 'gzip, br', 'Accept-Language': 'en-GB,en-US;q=0.9,en;q=0.8', 'Cdn-Loop': 'cloudflare', 'Cf-Access-Authenticated-User-Email': '[email protected]', 'Cf-Access-Jwt-Assertion':
Proxy config set to:
use_x_forwarded_for: true
trusted_proxies:
- 192.168.2.0/24
- 103.21.244.0/22
- 103.22.200.0/22
- 103.31.4.0/22
- 104.16.0.0/12
- 108.162.192.0/18
- 131.0.72.0/22
- 141.101.64.0/18
- 162.158.0.0/15
- 172.64.0.0/13
- 173.245.48.0/20
- 188.114.96.0/20
- 190.93.240.0/20
- 197.234.240.0/22
- 198.41.128.0/17
Been scratching my head. It used to work. - I could go back to sticking HA Proxy at the end of the cloudflare tunnel and then parsing the JWT which is also in the header and applying a header. I wondered if it might have some similarities to the nginx reverse proxy posts around the auth failure message. There’s not enough debug to see if auth_header successfully parsed the header which is present.
Fixed this - had an MTLS rule applying upstream in cloudflare over /api and didn’t have the certificate loaded on the device…
The way I have decided to go about remote access via the HA app using cloudflare tunnels has just been using the WARP app and allow authentication via WARP on my access app. It isn’t ideal but within the WARP app on my phone I have configured it to exclude every app except for home assistant in hopes that it wont demonstrate the same passive battery drain that having VPNs open all the time tend to do on android.
My setup was working fine, but stopped working a couple of weeks ago. All devices were showing “offline” in the Google Home app. Curiously, they would work fine from the pop-up that was displayed after a “sync my devices” command – just the regular list of devices was an issue.
After trying our with CloudFlare configs, I found out one of the ranges from this post had to be updated (66.249.80.0/29 to 66.249.80.0/20, based on Expose Home Assistant For Google IPs only- IPV4 only).
My new (working) list is:
108.177.0.0/17
192.178.0.0/15
66.102.0.0/20
74.125.0.0/16
66.249.80.0/20
Thank you, made the change!
Hi I know this was a while ago but I am stugggling getting this working with my ios app, I have a tunnel from cf and an application setup to protect my ha login, I am not using a proxy as of now and just have the header set to " username_header: Cf-Access-Authenticated-User-Email
" but for the life of me I cant get this working at all, I also need to do a bypass for smart things, if you could give me some pointers on your setup to get this working with cf access I would greatly appreciate it, if it helps I do have another proxy I can use which lives in the same subnet as HA is running as an os.
I found it easier to interact with cloudflared directly. I had all sorts of problems trying to use the addon and had an epiphany moment where I was like… Why am i using an addon?
With this approach, the only difference is the proxy settings are updated:
http:
use_x_forwarded_for: true
trusted_proxies:
- 127.0.0.1 # This because cloudflared runs on the same machine so HA needs to "trust" localhost so that cloudflared can forward it.
- ::1 # Same as above but IPV6
- 192.168.0.0/24 # This because this is the mask for this network
Adjust the trusted proxy address to point to whereever your cloudflared tunnel is running. if its on the same machine you can do a cut and paste of the above.
The network mask will be whatever the mask is for HA 192.168.0.X, usually, but sometimes it can be 192.168.1.X. you can find out by going to your local instance via its ip address.
Can someone explain me how i can get this working with a subdomain?
I allready have a domain.
I changed the DNS for this domain to cloudflare and i try adding an ‘A-record’
But this A-record does not appear in the list from the link i got from the cloudflare addon (only my main domain is displayed) but since this is allready used for a website i can not use this…