-
Notifications
You must be signed in to change notification settings - Fork 2
Guide: Securing URSYS
The URSYS Build Framework utilizes both Express webservers and WebSocket servers running on localhost, and do not support https. This is sufficient for developing on your own machine, but if you want to deploy to a remote server you want at least secure http (https). This guide provides details on how to achieve that.
While our Node Express code uses plain http, Nginx can both handle https and redirect websocket connections.
- Follow Guide: Ubuntu Server Administration to set up nginx with let's encrypt
- Add the following location to the nginx https server block, which in this example will redirect https://ursys.dsri.xyz/app/ to the express app
server_name ursys.dsri.xyz ;
location /app/ {
proxy_pass http://127.0.0.1:8080/;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $server_name;
proxy_read_timeout 7200; # 2 hours
}
-
Restart nginx by first testing the config with
nginx -t
thensystemctl restart nginx
Make sure your Express app's listen()
is using the address http://127.0.0.1:8080
to force IPV4, then browser to the route (here it's set to app) on the Nginx server.
This proxy is forwarding the url to 127.0.0.1:8080
without additional route information. To support that, you will need to rewrite your nginx location block and express server accordingly to handle routes and route parameters.
This particular location block redirects a single path like http://ursys.dsri.xyz/app/
to the Express app running on 127.0.0.1:8080
, handling websocket traffic as well. The http
connection is changed to https
behind the scenes through the nginx configuration.
Here's my complete nginx config for ursys.dsri.xyz
as of the time of this writing. The top block is for https, and the second for handling http redirects to https. Note that Let's Encrypt manages the security certificates through its certbot
.
server {
root /var/www/ursys_dsri_xyz/html;
index index.html index.htm index.nginx-debian.html;
server_name ursys.dsri.xyz ;
location /app/ {
proxy_pass http://127.0.0.1:8080/;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $server_name;
proxy_read_timeout 7200; # 2 hours
}
location / {
try_files $uri $uri/ =404;
}
listen [::]:443 ssl ipv6only=on; # managed by Certbot
listen 443 ssl; # managed by Certbot
ssl_certificate /etc/letsencrypt/live/dsri.xyz/fullchain.pem; # managed by Certbot
ssl_certificate_key /etc/letsencrypt/live/dsri.xyz/privkey.pem; # managed by Certbot
include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot
}
server {
if ($host ~ ^[^.]+\.dsri\.xyz$) {
return 301 https://$host$request_uri;
} # managed by Certbot
if ($host = ursys.dsri.xyz) {
return 301 https://$host$request_uri;
} # managed by Certbot
listen 80;
listen [::]:80;
server_name ursys.dsri.xyz ;
return 404; # managed by Certbot
}
Note
The proxy settings specific for websockets are proxy_http_version
, "Upgrade", and "Connection". WebSocket requires HTTP/1.1. The Upgrade and Connection headers are passed-through to the WebSocket Server library in the Express application so it can configure itself appropriately.