← Back to posts

How I built my personal blog on AWS for free

I wanted a place to document what I learn. Not a LinkedIn post here and there — an actual blog I own and control.

The goal was simple: a fast, lightweight blog that I could automate with AI later. No databases, no plugins, no maintenance overhead.

Here’s exactly how I built it.


The setup


Step 1 — Install Nginx

Apache is fine, but for serving static files Nginx is simpler and lighter.

sudo dnf install nginx -y
sudo systemctl start nginx
sudo systemctl enable nginx

Check it’s running:

sudo systemctl status nginx
# Active: active (running) ✓

Step 2 — Install Hugo

Hugo isn’t in Amazon Linux’s default repositories, so install it manually:

wget https://github.com/gohugoio/hugo/releases/download/v0.145.0/hugo_0.145.0_linux-amd64.tar.gz
tar -xzf hugo_0.145.0_linux-amd64.tar.gz
sudo mv hugo /usr/local/bin/
rm hugo_0.145.0_linux-amd64.tar.gz LICENSE README.md
hugo version

Hugo is a static site generator — it takes Markdown files and converts them into a complete HTML website in milliseconds. No database, no PHP, no runtime dependencies.


Step 3 — Create the site and theme

cd ~
hugo new site lucianosblog
cd lucianosblog
hugo new theme luciano

Hugo generates the folder structure automatically. The theme goes in themes/luciano/layouts/ — from there you control every page with plain HTML templates.

I built a custom dark theme from scratch: fixed navigation, animated hero section, category grid, article cards, and a footer with social links. The CSS is around 120 lines.


Step 4 — Configure Nginx to serve Hugo

Tell Nginx where Hugo puts its generated files:

sudo tee /etc/nginx/conf.d/lucianosblog.conf << 'EOF'
server {
    listen 80 default_server;
    server_name _;
    root /path/to/your/site/public;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }
}
EOF

sudo nginx -t && sudo systemctl reload nginx

Build the site and test locally:

hugo build
curl -I http://localhost
# HTTP/1.1 200 OK ✓

Step 5 — SSL with Let’s Encrypt

Cloudflare was set to Full (strict) mode — which requires a valid certificate on the server. Without it, you get a 521 error.

sudo dnf install certbot python3-certbot-nginx -y
sudo certbot --nginx -d lucianosblog.com -d www.lucianosblog.com

Certbot detects your Nginx config automatically, gets the certificate from Let’s Encrypt, and updates the config to redirect HTTP to HTTPS. The whole thing takes about 60 seconds.


The result

A live blog at lucianosblog.com with:


If you found this useful or have questions, connect with me on LinkedIn.