How To Host Cloudflare Behind Nginx
By MzFit
- 3 minutes read - 453 wordsI ran into a situation that seems counterintuitive. Nginx is a web server for hosting web content. Cloudflare is a content delivery network. You normally put your content delivery network in front of your web web server to speed things up. I recently needed to put Nginx in front of Cloudflare and I figured it might be worthwhile documenting in case someone else runs into the same situation.
My main web site https://mzfit.app provides a web application for finding YouTube workout videos. It’s built using the go programming language and I have nginx routing traffic to the go app. At one point I decided to add my blog (the one you’re reading now) into the web app, so I built some custom functions into the web app for blogging.
However, it turns out that building a nice looking web site takes a lot of time. So I decided to switch to Hugo for blogging. This presented a problem where I needed to have Cloudflare route traffic for https://mzfit.app/w/youtube/browse to my Golang app, but I needed to have Cloudflare route traffic to a Cloudflare pages app where my blog is published.
There is probably a way to do this natively in Cloudflare, but after searching for a while (the details are a little fuzzy to me now) I either couldn’t find a good way to do this or the only way to do it was by enabling some paid features. (NOTE: Cloudflare offers some very nice features and if you’re in a financial position to support them, I do recommend it.)
I decided to investigate using Nginx to route traffic to the cloudflare instance, so the flow looks something like this:
Cloudflare -> Nginx -> Golang web app
-> Cloudflare Pages (blog)
Naively, I tried setting up Nginx with a simple reverse proxy to the Cloudlate Pages URL.
However, this did not work. And it took me a while to find a random mention in a cryptic stack overflow entry that clued me in (apologies, I don’t seem to have saved the exact stack overflow link. I really owe that guy a beer.)
The trick in the nginx config was to enable the proxy_ssl_server_name on and set the proxy_ssl_protocols:
location /blog {
proxy_pass https://NGINX_CLOUDFLARE;
proxy_set_header Host 'NGINX_CLOUDFLARE';
proxy_ssl_server_name on;
proxy_ssl_protocols TLSv1 TLSv1.1 TLSv1.2 TLSv1.3;
}
This allowed nginx to pass the traffic to Cloudflare pages with the appropriate headers for it to serve up my Cloudflare Pages hosted blog.
Since Cloudflare sits in front of the whole site, it caches both the golang web app and the Pages app.
As with any tech problems, this involved a lot of research to find the 2 line magic incantation.
Hopefully this helps someone from the future.