Setting up an NGINX Reverse Proxy with SSL
A reverse proxy is a function of a web server that allows it to forward requests onto other web servers. Typically they are set up in combination with a wildcard SSL certificate, allowing each subdomain to go to a different server. Apache2 and NGINX can both function as reverse proxies, but NGINX is much easier to set up!
Installing NGINX
Install using apt
First, install nginx using apt:
sudo apt install nginx
Testing with telnet
Telnet is great for testing TCP ports. NGINX listens on TCP port 80 by default, so we can test it with telnet:
telnet 127.0.0.1 80
If the server is responding correctly, you should see an output similar to below:
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
Configuring NGINX
NGINX configuration files are stored in /etc/nginx/ - the site configuration files are stored in sites-available/, then these are enabled by creating a symbolic link to them in sites-enabled/
Disabling the default site configuration file
Now that we know the server is running, we are going to disable the default NGINX configuration file. This is so that we can create a new one that is more focused around the reverse proxy abilities of NGINX.
To remove the default configuration file, run this command:
sudo rm /etc/nginx/sites-enabled/default
Creating a new site configuration file
We will now create a new site configuration file, using our domain name as the file name:
sudo nano /etc/nginx/sites-available/YOUR.DOMAIN
Here is an example template, which retains NGINX's default site configuration for the root domain and does reverse proxy for a subdomain to a Proxmox server:
# We are defining our Let's Encrypt certificate here
# If your NGINX server will serve multiple domains, you will instead need to place it within the 443 definition
ssl_certificate /etc/letsencrypt/live/YOUR.DOMAIN/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/YOUR.DOMAIN/privkey.pem;
# Required when reverse proxying to a Proxmox server
map $http_upgrade $connection_upgrade {
default upgrade;
'' close;
}
# This will forward all HTTP requests to HTTPS
server {
listen 80;
listen [::]:80;
server_name *.YOUR.DOMAIN;
rewrite ^ https://$host$request_uri? permanent;
}
# This will serve NGINX's default web page, via HTTPS
server {
listen 443 ssl;
listen [::]:443 ssl;
server_name YOUR.DOMAIN;
# Define the web root
root /var/www/html;
# Add index.php to the list if you are using PHP
index index.html index.htm index.nginx-debian.html;
location / {
# First attempt to serve request as file, then
# as directory, then fall back to displaying a 404.
try_files $uri $uri/ =404;
}
}
# This subdomain will reverse proxy requests to a Proxmox web interface
server {
listen 443 ssl;
listen [::]:443 ssl;
server_name proxmox.YOUR.DOMAIN;
location / {
proxy_pass https://YOUR.PROXMOX.IP.ADDRESS:8006;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
}
Once modified to suit your setup, use Control-S to save and Control-C to quit nano.
Enabling the new configuration file
We now have a new configuration file, and we are going to enable it by creating a symbolic link:
sudo ln -s /etc/nginx/sites-available/YOUR.DOMAIN /etc/nginx/sites-enabled/YOUR.DOMAIN
Testing the configuration
We can now run nginx -t in order to test the new configuration file:
sudo nginx -t
Assuming all is well, you should see an output similar to below:
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful
Restarting NGINX
Once we've confirmed that the configuration file tests successfully, we can apply it by restarting the NGINX service:
sudo systemctl restart nginx
Testing port 443 with telnet
We already know that NGINX was listening on TCP port 80, but since we have just enabled SSL, we want to make sure that it's also listening on port 443:
telnet 127.0.0.1 443
The output should be similar to before:
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
No Comments