web
certbot
docker
nginx
In this article, we are going to deploy a production server that we created on docker section
The flow will like below:
Below is the overall idea of this application
Nginx is going to listen on 80 port as an reverse proxy. When it gets certain request, it will transfer it to the responsible port service.
In this case, when a user accesses https://www.colorfullife.ml, Nginx will transfer it to localhost:3000 port in which our node server is located.
apt install nginx
cd into /etc/nginx/sites-available
and then touch one more file called colorfullife.ml
server {
listen 80 default_server;
listen [::]:80 default_server;
root /var/www/html;
server_name colorfullife.ml www.colorfullife.ml;
location / {
proxy_pass http://localhost:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
}
Then reload the nginx server by
sudo systemctl reload nginx
When try to access the public IP address of our VPS, we can see the nginx welcome page.
Firstly, we need to have a Domain name. We register one from freenom called "colorfullife.ml".
We then direct the Aname in the DNS config page to our VPS public IP
Then when we enter the url with our domain, we can see the same nginx welcome page. It means the DNS successfully resolve the url to our public ip address.
Now we need to make the access secured by adding SSL certification to allow https protocol access.
We are making use of "certbot" package.
sudo apt-get install certbot
sudo apt-get install python3-certbot-nginx
And we can obtaining an SSL Certificate for our domain url
Reference doc: How To Secure Nginx with Let's Encrypt on Ubuntu 18.04
sudo certbot --nginx -d www.colorfullife.ml
Now we can see the same nginx welcome page using "https"
Now we need to route the request when nginx gets the request from "https://www.colorfullife.ml"
server {
listen 80 default_server;
listen [::]:80 default_server;
# SSL configuration
#
# listen 443 ssl default_server;
# listen [::]:443 ssl default_server;
#
# Note: You should disable gzip for SSL traffic.
# See: https://bugs.debian.org/773332
#
# Read up on ssl_ciphers to ensure a secure configuration.
# See: https://bugs.debian.org/765782
#
# Self signed certs generated by the ssl-cert package
# Don't use them in a production server!
#
# include snippets/snakeoil.conf;
root /var/www/html;
# Add index.php to the list if you are using PHP
index index.html index.htm index.nginx-debian.html;
server_name _;
location / {
# First attempt to serve request as file, then
# as directory, then fall back to displaying a 404.
#try_files $uri $uri/ =404;
proxy_pass http://localhost:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
# pass PHP scripts to FastCGI server
#
#location ~ \.php$ {
# include snippets/fastcgi-php.conf;
#
# # With php-fpm (or other unix sockets):
# fastcgi_pass unix:/var/run/php/php7.4-fpm.sock;
# # With php-cgi (or other tcp sockets):
# fastcgi_pass 127.0.0.1:9000;
#}
# deny access to .htaccess files, if Apache's document root
# concurs with nginx's one
#
#location ~ /\.ht {
# deny all;
#}
}
# Virtual Host configuration for example.com
#
# You can move that to a different file under sites-available/ and symlink that
# to sites-enabled/ to enable it.
#
#server {
# listen 80;
# listen [::]:80;
#
# server_name example.com;
#
# root /var/www/example.com;
# index index.html;
#
# location / {
# try_files $uri $uri/ =404;
# }
#}
server {
# SSL configuration
#
# listen 443 ssl default_server;
# listen [::]:443 ssl default_server;
#
# Note: You should disable gzip for SSL traffic.
# See: https://bugs.debian.org/773332
#
# Read up on ssl_ciphers to ensure a secure configuration.
# See: https://bugs.debian.org/765782
#
# Self signed certs generated by the ssl-cert package
# Don't use them in a production server!
#
# include snippets/snakeoil.conf;
root /var/www/html;
# Add index.php to the list if you are using PHP
index index.html index.htm index.nginx-debian.html;
server_name www.colorfullife.ml; # managed by Certbot
location / {
# First attempt to serve request as file, then
# as directory, then fall back to displaying a 404.
#try_files $uri $uri/ =404;
proxy_pass http://localhost:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
# pass PHP scripts to FastCGI server
#
#location ~ \.php$ {
# include snippets/fastcgi-php.conf;
#
# # With php-fpm (or other unix sockets):
# fastcgi_pass unix:/var/run/php/php7.4-fpm.sock;
# # With php-cgi (or other tcp sockets):
# fastcgi_pass 127.0.0.1:9000;
#}
# deny access to .htaccess files, if Apache's document root
# concurs with nginx's one
#
#location ~ /\.ht {
# deny all;
#}
listen [::]:443 ssl ipv6only=on; # managed by Certbot
listen 443 ssl; # managed by Certbot
ssl_certificate /etc/letsencrypt/live/www.colorfullife.ml/fullchain.pem; # managed by Certbot
ssl_certificate_key /etc/letsencrypt/live/www.colorfullife.ml/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 = www.colorfullife.ml) {
return 301 https://$host$request_uri;
} # managed by Certbot
listen 80 ;
listen [::]:80 ;
server_name www.colorfullife.ml;
return 404; # managed by Certbot
}
Everything is done, we can access our docker container application by accessing "https://www.colorfullife.ml"
After reading through the official doc, I realized that directly modifying sites-availale/default is not a recommanded apporach
In most cases, administrators will remove this file from sites-enabled/ and leave it as reference inside of sites-available where it will continue to be updated by the nginx packaging team.
So, we need to classify our structure a bit.
Firstly comment out all the content in sites-available/default.
Secondly, I realized that actually the colorfullife.ml file in sites-aviable/ has not been used at all.
Lets change the name more explicitly (www.colorfullife.ml) and also change the content
server {
root /var/www/html;
index index.html index.htm index.nginx-debian.html;
server_name services.dev-eric.ml; # managed by Certbot
location / {
proxy_pass http://localhost:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
listen [::]:443 ssl ipv6only=on; # managed by Certbot
listen 443 ssl; # managed by Certbot
ssl_certificate /etc/letsencrypt/live/services.dev-eric.ml/fullchain.pem; # managed by Certbot
ssl_certificate_key /etc/letsencrypt/live/services.dev-eric.ml/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
}
Only changing the content will not enable this setting.
We will need to link this file to sites-enabled to enable this config.
So, cd into the sites-enabled/ and run following command
sudo ln -s ../sites-available/www.colorfullife.ml
And then we can see there is symbolic link with the same name (www.colrfullife.ml) is created into sites-enabled/.
It mean the config in sites-available/www.colorfullife.ml has been enabled.
After reloading the nginx service, and access www.colorfullife.ml, it will be working as before.
According to the document, The reason to make this classification is making the site control more systematic. We can disable or enable certain proxy or site by just create a symboic link. Else disable by remove the symboic link.