Websocket connections not working through Cloudflare Tunnels

Describe the bug
Accordingly to the docs websockets are supported by cloudflare, but after I did set a hostname in Zero trust Dashboard → Access → Tunnels → mytunnel → Public Hostname

This is the hostname config:

subdomain: mysubdomain
domain: mydomain.com

type: HTTPS
url: localhost:443
noTLSVerify: true

I can get access to my site perfectly, here’s the problem, my server web-application, needs to stream content from multiple websocket ports, specifically from port 2100 to port 2140, this is because my web-application is divided in multiple modules and every module has to communicate through a websocket port… here is my apache https configuration:

LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_http_module modules/mod_proxy_http.so
LoadModule proxy_wstunnel_module modules/mod_proxy_wstunnel.so
LoadModule vhost_alias_module modules/mod_vhost_alias.so

Listen 443 https

<IfDefine ENABLE_TLS13>
	***some tls content here***
</IfDefine>

<IfDefine !ENABLE_TLS13>
	***some tls content here***
</IfDefine>

SSLHonorCipherOrder On
SSLPassPhraseDialog  builtin

SSLSessionCache        "shmcb:${SRVROOT}/logs/ssl_scache(512000)"
SSLSessionCacheTimeout  300

AddType application/x-x509-ca-cert .crt
AddType application/x-pkcs7-crl    .crl

<FilesMatch "\.(cgi|shtml|phtml|php)$">
	SSLOptions +StdEnvVars
</FilesMatch>
<Directory "${SRVROOT}/cgi-bin">
	SSLOptions +StdEnvVars
</Directory>

BrowserMatch "MSIE [2-5]" nokeepalive ssl-unclean-shutdown downgrade-1.0 force-response-1.0

CustomLog "${SRVROOT}/logs/ssl_request.log" "%t %h %{SSL_PROTOCOL}x %{SSL_CIPHER}x \"%r\" %b" env=HTTPS

<VirtualHost *:443>

	SSLEngine On
        SSLProxyEngine On
	# ServerName mydomain.com:443

#Tried with and without all this block

# RewriteEngine on
# RewriteCond %{HTTP:Upgrade} websocket [NC]
# RewriteCond %{HTTP:Connection} upgrade [NC]
# RewriteRule ^/?(.*) "ws://localhost:2100/$1" [P,L]
# ProxyRequests On
# ProxyPreserveHost On

	SSLCertificateFile "C:\Certbot\archive\sub.mydomain.com\cert1.pem"
	SSLCertificateKeyFile "C:\Certbot\archive\sub.mydomain.com\privkey1.pem"

	# HARBOUR BEGIN - AUTO-GENERATED

# Module Accounting
ProxyPass /harbour/2100 ws://127.0.0.1:2100/harbour
ProxyPassReverse /harbour/2100 ws://127.0.0.1:2100/harbour
ProxyPass /monitor/2100 ws://127.0.0.1:2100/monitor
ProxyPassReverse /monitor/2100 ws://127.0.0.1:2100/monitor

# Module Reservations
ProxyPass /harbour/2102 ws://127.0.0.1:2102/harbour
ProxyPassReverse /harbour/2102 ws://127.0.0.1:2102/harbour
ProxyPass /monitor/2102 ws://127.0.0.1:2102/monitor
ProxyPassReverse /monitor/2102 ws://127.0.0.1:2102/monitor

# Module Reception
ProxyPass /harbour/2101 ws://127.0.0.1:2101/harbour
ProxyPassReverse /harbour/2101 ws://127.0.0.1:2101/harbour
ProxyPass /monitor/2101 ws://127.0.0.1:2101/monitor
ProxyPassReverse /monitor/2101 ws://127.0.0.1:2101/monitor

# Module Banking
ProxyPass /harbour/2105 ws://127.0.0.1:2105/harbour
ProxyPassReverse /harbour/2105 ws://127.0.0.1:2105/harbour
ProxyPass /monitor/2105 ws://127.0.0.1:2105/monitor
ProxyPassReverse /monitor/2105 ws://127.0.0.1:2105/monitor

# Module Owners
ProxyPass /harbour/2104 ws://127.0.0.1:2104/harbour
ProxyPassReverse /harbour/2104 ws://127.0.0.1:2104/harbour
ProxyPass /monitor/2104 ws://127.0.0.1:2104/monitor
ProxyPassReverse /monitor/2104 ws://127.0.0.1:2104/monitor

# Module Restaurant
ProxyPass /harbour/2106 ws://127.0.0.1:2106/harbour
ProxyPassReverse /harbour/2106 ws://127.0.0.1:2106/harbour
ProxyPass /monitor/2106 ws://127.0.0.1:2106/monitor
ProxyPassReverse /monitor/2106 ws://127.0.0.1:2106/monitor

# Module Hotel Configuration
ProxyPass /harbour/2107 ws://127.0.0.1:2107/harbour
ProxyPassReverse /harbour/2107 ws://127.0.0.1:2107/harbour
ProxyPass /monitor/2107 ws://127.0.0.1:2107/monitor
ProxyPassReverse /monitor/2107 ws://127.0.0.1:2107/monitor

# Module Payroll
ProxyPass /harbour/2108 ws://127.0.0.1:2108/harbour
ProxyPassReverse /harbour/2108 ws://127.0.0.1:2108/harbour
ProxyPass /monitor/2108 ws://127.0.0.1:2108/monitor
ProxyPassReverse /monitor/2108 ws://127.0.0.1:2108/monitor

# Module Accounts Payable
ProxyPass /harbour/2109 ws://127.0.0.1:2109/harbour
ProxyPassReverse /harbour/2109 ws://127.0.0.1:2109/harbour
ProxyPass /monitor/2109 ws://127.0.0.1:2109/monitor
ProxyPassReverse /monitor/2109 ws://127.0.0.1:2109/monitor

# Module Accounts Receivable
ProxyPass /harbour/2110 ws://127.0.0.1:2110/harbour
ProxyPassReverse /harbour/2110 ws://127.0.0.1:2110/harbour
ProxyPass /monitor/2110 ws://127.0.0.1:2110/monitor
ProxyPassReverse /monitor/2110 ws://127.0.0.1:2110/monitor

# Module Payroll Configuration
ProxyPass /harbour/2111 ws://127.0.0.1:2111/harbour
ProxyPassReverse /harbour/2111 ws://127.0.0.1:2111/harbour
ProxyPass /monitor/2111 ws://127.0.0.1:2111/monitor
ProxyPassReverse /monitor/2111 ws://127.0.0.1:2111/monitor

# Module Inventory
ProxyPass /harbour/2112 ws://127.0.0.1:2112/harbour
ProxyPassReverse /harbour/2112 ws://127.0.0.1:2112/harbour
ProxyPass /monitor/2112 ws://127.0.0.1:2112/monitor
ProxyPassReverse /monitor/2112 ws://127.0.0.1:2112/monitor

# Module Fixed Assets
ProxyPass /harbour/2113 ws://127.0.0.1:2113/harbour
ProxyPassReverse /harbour/2113 ws://127.0.0.1:2113/harbour
ProxyPass /monitor/2113 ws://127.0.0.1:2113/monitor
ProxyPassReverse /monitor/2113 ws://127.0.0.1:2113/monitor

# Module Spa
ProxyPass /harbour/2114 ws://127.0.0.1:2114/harbour
ProxyPassReverse /harbour/2114 ws://127.0.0.1:2114/harbour
ProxyPass /monitor/2114 ws://127.0.0.1:2114/monitor
ProxyPassReverse /monitor/2114 ws://127.0.0.1:2114/monitor

# Module Events
ProxyPass /harbour/2115 ws://127.0.0.1:2115/harbour
ProxyPassReverse /harbour/2115 ws://127.0.0.1:2115/harbour
ProxyPass /monitor/2115 ws://127.0.0.1:2115/monitor
ProxyPassReverse /monitor/2115 ws://127.0.0.1:2115/monitor

# Module Tours
ProxyPass /harbour/2116 ws://127.0.0.1:2116/harbour
ProxyPassReverse /harbour/2116 ws://127.0.0.1:2116/harbour
ProxyPass /monitor/2116 ws://127.0.0.1:2116/monitor
ProxyPassReverse /monitor/2116 ws://127.0.0.1:2116/monitor

# HARBOUR END - AUTO-GENERATED

	DocumentRoot "C:\my-path\www"
	CustomLog "${SRVROOT}/logs/ssl_request.log" \
		"%t %h %{SSL_PROTOCOL}x %{SSL_CIPHER}x \"%r\" %b"

	<Directory "C:\my-path\www">

		Options +ExecCGI +Indexes +FollowSymLinks

		DirectoryIndex index.html index.exe

		AllowOverride All
		Require all granted

		Require all granted

	</Directory>

</virtualhost>

When I serve my web-app without cloudflare tunnels, everything works as expected… no errors… but with cloudflare tunnel my site loads, but as soon as I launch any modules from my webapp, this is shown in console:

webSocket address:  wss://sub.mydomain.com/harbour/2100
webview.js:706 WebSocket connection to 'wss://sub.mydomain.com/harbour/2100' failed: 
initialize @ webview.js:706
(anonymous) @ webview.js:4264
dispatch @ jquery.min.js:2407
y.handle @ jquery.min.js:2312

Any ideas about how to make it work with cloudflare tunnel?

Thanks in advance, if there’s any other information you need from me, please let me know.

Cloudflare does not listen on those ports, see Network ports · Cloudflare Fundamentals docs.

That can be changed with an Enterprise Account and the Spectrum add-on ($$$$).

Otherwise, if you want to use Cloudflare, you’d have to use different hostnames instead of different ports on the frontend. The backend could remain the same.

1 Like

I am having a similar issue as the op with an erp, however your response may not be correct. The documentation you have referred us to is related to proxied connections. Both the op and myself are using a tunnel, not a proxy. Any help would be appreciated. I am looking to pay for my subs rather than using the free version that is only community supported, but only if i can demonstrate that i can get it to work.

Cloudflare listens only on the listed ports.

Whether the connection to your server is made via a tunnel or proxied DNS makes no difference, because Cloudflare doesn’t receive the request in the first place.

1 Like

I dont want to be pulling your response to bits, i know you are trying to help, but that document repeatdely states proxy, not tunnel:-

"# Network ports

Learn which network ports Cloudflare proxies by default and how to enable Cloudflare’s proxy for additional ports."

"## How to enable Cloudflare’s proxy for additional ports

If traffic for your domain is destined for a different port than the ones listed above, for example you have an SSH server that listens for incoming connections on port 22, either:

  • Change your subdomain to be gray-clouded, via your Cloudflare DNS app, to bypass the Cloudflare network and connect directly to your origin."

Its very specifically proxy, never mentions tunnel, which you would hope would be designed to be flexible for your applications in their current config, not having to redesign or configure your apps to work with cloudflare tunnel.

I have found other posts regarding this, specifically about the tunnel:-

https://community.cloudflare.com/t/tunnel-with-websockets/318111/3

This documentation seems to be related to tunnels, and it mentions ports outside of the ones listed in the article that was posted such as rdp (3389), 2222, etc:-

https://developers.cloudflare.com/cloudflare-one/connections/connect-networks/configure-tunnels/local-management/configuration-file

Its my first day on this, and im struggling to understand it, but i don’t think you are right if this article is for tunnels.

Anybody from cloudflare able to weigh in on this

Cloudflare is a proxy, whether you use a tunnel or proxied DNS entries to connect to your origin. “Proxy” means that all requests are sent to Cloudflare first and not directly to your server.

You can use whatever ports you want with tunnels, but that requires you to install the tunnel software both on the client and the server.

But that’s not going to help you if you want to create a public website. To be fair, I just assumed that you and the OP wanted to create a public website.

I dont know what the op’s use case is, but mine is to connect sales people to our erp, as their have been complaints of using our ssl vpn, always being prompted for 2fa to connect.

When you say that requires you to install the tunnel software both on the client and server, do you mean cloudflarer on the server, and warp on the client? if so, i have warp setup on a workstation, all connected and authenticated, and even though the traffic appears to be going via warp, same issue

I don’t quite understand that part, I can use virtually any port I like with cloudflare tunnels, I have multiple different ports which are not listed there, and they all just work for any localhost app I serve, the only thing I have installed on my server is cloudflared, and that’s pretty much I need…

In my case, I have a PMS software that works with modules, every module is streamed to the webpage through a websocket connection for each one… doesn’t seems like any “against” the rules or permitted ports policy as I understand… I may be wrong, I just don’t quite understand why it’s not working.

thats how i took the tunnel documentation, thank you for confirming that you are both using websockets, and that they are not listed, and that its working. I imagine their is some configuration i need to do. I dont know if yours used the same ports as your http (not a web expert so if thats wrong, please be gentle), my https and websocket port are completely different. Im guessing maybe thats the issue, but i dont know as i have been at this a day. im contemplating buying 1 seat and raising a support request, lol

I’ve used Cloudflared on both server and client.

The GitHub states that this should be possible with Warp as well, but I’ve not tried that yet.

Ive bought a zero trust seat and put in a ticket to get support from cloudflare for my proof of concept setup.