HexTxt

Caddy Configuration Notes

Technology
organized cyberpunk web server engineer

Image generated by deepai.org -- caddy web server configuration, happy blogger, simple life

In early 2023 I decided I wanted to move my blogs to a VPS. Some time before that I had already moved from Wordpress to Hugo. Which meant all I really needed was a spot to server static files. Maybe a VPS was overkill but I found a cheap one with decent reviews.

Plus, I really do like having full access to my little slice of the server via the command line and Emacs. So for my own future reference and maybe to help you out I am posting an example entry for the Caddy web server configuration file.

Why use the Caddy web server?

Mostly, I wasn’t very excited about configuring Apache. I actually have no idea how easy or hard of a project that would be. Before I took the leap onto that learning curve to find out I discovered the Caddy web server. Which has definitely delivered on ease of setup and having automatic SSL configuring built-in is pretty nice. One less thing to figure out.

Example Caddyfile

example1.com {
	encode zstd gzip
	root * /var/www/example1
	file_server
    
    handle_errors {
		@404 {
			expression {http.error.status_code} == 404
		}
		rewrite @404 /404.html
		file_server
	}

	log {
		output file /var/log/caddy/example1-access.log {
			roll_disabled
		}
	}
}

example2.com {
	encode zstd gzip
	root * /var/www/example2
	file_server    

    handle_errors {
		@404 {
			expression {http.error.status_code} == 404
		}
		rewrite @404 /404.html
		file_server
	}
    
	log {
		output file /var/log/caddy/example2-access.log {
			roll_disabled
		}
	}
}

example3.com {
	encode zstd gzip
	root * /var/www/example3
	file_server
   	
    handle_errors {
		@404 {
			expression {http.error.status_code} == 404
		}
		rewrite @404 /404.html
		file_server
	}
    
	log {
		output file /var/log/caddy/example3-access.log {
			roll_disabled
		}
	}
}

Caddyfile Configuration Explained

First, gzip and zstd compression are enabled. Compression is supposed to help with site speed which is supposed to be helpful with seo.

	encode zstd gzip

Next, Caddy is being pointed to where the website lives.

	root * /var/www/example1

Now, we are telling Caddy to act as a static file server. Being a static site this makes sense.

	file_server

Caddyserver Error Handling

Make sure to handle missing page errors. If you don’t handle the 404 page not found error your reader might end up at a blank page. Like how my site was set up for a while.

Keep readers at your site with a helpful 404 page. All you need is a 404.html page and the following addition to Caddyfile.

	handle_errors {
		@404 {
			expression {http.error.status_code} == 404
		}
		rewrite @404 /404.html
		file_server
	}

While you are at it you can take a few minute and make the 404 page friendly and helpful. Some web developers have very creative and funny error pages. Look around for examples.

At the very least give readers some options for exploring your site more. For an example check out this 404 page.

Log Files with Logrotate

Finally, we have logging. This configuration is to allow Caddy to add to the web traffic log file indefinitely. Sound dangerous? Run out of disk space dangerous?

I wanted a little more control over where old logs were stored and how long they were kept. Linux has logrotate to manage such details so I limited Caddy to being a log producer and let logrotate take over the rest of the log file handling.

	log {
		output file /var/log/caddy/example1-access.log {
			roll_disabled }

Then to have Caddy recognize the configuration:

$ sudo systemctl reload caddy

How did I configure logrotate? In /etc/logrotate.d I created a file named caddy. In that file I configured logrotate to do the following when it ran.

/var/log/caddy/*.log {
        monthly
        rotate 120
        olddir /var/log/caddy/archive
        copytruncate
        dateext
        dateformat _%Y-%m-%d
        compress
}

You don’t need to restart logrotate after making edits. The program is run with cron. Next time it runs the new config will be used.

With this configuration logrotate will:

So far, logrotate is getting things done how I envisioned. At month end the prior month log data is being sent to the archive directory dated and compressed.

And with ten years before deletion of old log files starts I have plenty of time to move them to a safe directory for further processing or storage.

What am I doing with the logs? Why, keeping track of my web traffic. I don’t want Google Analytics (or alternatives) invading your privacy or slowing down my website.

Server logs work for me. They can even be viewed from the command line using the very neat Goaccess log viewer. More on Goaccess in another article.

Share with Friends!
LinkedIn
Reddit
Hacker News