Geht wählen! Am 26. September 2021 ist Bundestagswahl in Deutschland, wählt Annalena Baerbock für zukunftssichere Klima-, Digital- und Sozialpolitik.. Mehr infos zum Wahlprogramm auf gruene.de 🗳💚🌻

Proxy websocket connections with Apache2

How to configure Apache2 to pass through web socket connections

Written by Kevin Gimbel on , 🍿 2 min. read

Recently I had to adjust an Apache Virtual Host to allow proxying of Web Socket requests to a service running on localhost which would also accept HTTP requests on the same port.

The problem

The service in question was Loki, the "Prometheus, but for logs" from Grafana. At Synoa we've grown to love Prometheus and Grafana, so the choice to do our centralized log management with Loki came naturally; Especially since Loki is a lot simpler in its architecture and easier to operate with a small ops team; But that's stuff for another blog post. :)

Without the Socket proxy the "Live View" on incoming logs and the "Show Context" button which shows surrounding lines of a log in Grafana didn't work; Since I've had no experience with Web Sockets it took some time to figure out that the problem was the sockets didn't reach the backend service running on 127.0.0.1:3000 behind Apache2.

The solution

The solution was to configure Apache so it would proxy the web socket request to the websocket service (ws://127.0.0.1:3000/) explicitly if the request is marked as such with the Upgrade and Connection headers.

For this to work, we first need the proxy_wstunnel module.

# Enable module on Ubuntu
$ sudo a2enmod proxy_wstunnel

Then, we can adjust the vhost configuration file to include a rewrite rule (lines 4 to 7):

<VirtualHost *:443>
ServerName my.server.tld
SSLEngine On

RewriteEngine On
RewriteCond %{HTTP:Upgrade} websocket [NC]
RewriteCond %{HTTP:Connection} upgrade [NC]
RewriteRule ^/?(.*) "ws://127.0.0.1:3000/$1" [P,L]

ProxyPreserveHost On
ProxyPass / http://127.0.0.1:3000/
ProxyPassReverse / http://127.0.0.1:3000/
ProxyRequests off
</VirtualHost>

After making these changes and reloading Apache2, the Grafana Live Log view and Loki "Show Context" function was working again.

Further reading

Hi, I'm Kevin!

I'm a DevOps Engineer with a focus on automation and security. Before shifting into DevOps and cloud computing I worked as Front-End Developer, which is still a hobby and field of interest for me.

Hand-made vector avatar of Kevin Gimbel

I'm very passionated about a variety of games - digital, boardgames, and pen & paper; and also interested in Sci-Fi, Cyberpunk, and dystopian books. You can find out more on the about page.