Posted on March 21, 2016

Writing a new life in Hakyll

This week I’m on vacation.

Much to the confusion of many of my colleagues and friends, I like to use my time off of work to … work. I take the etimology of vacation seriously:

From the latin vacatio, meaning freedom, exemption, immunity from service, priviledge.

So vacations are my free (as in freedom) time to do what I like to do most. And that is usually studying.

So, this week I’m studying. :-)

I’ve been wanting to clean up my blog and remove it from Tumblr for a while now, and so this seemed like a nice opportunity to move it to Hakyll, host it on AWS, document everything and learn something new in the process.

But I wasn’t looking only for a replacement for Tumblr.

If I’m going to host my blog, then I don’t want to be worrying about machine failures or datacenter problems. So it needs be easily recreatable, where easily means with one command. It also needs to updates itself automatically after I commit an article to a git repo, so that I don’t have to rebuild it manually and can focus on just writing markdown and pushing to git.

So this is a bit more work than just installing Hakyll somewhere, but it’s also a learning experience and a safer approach to hosting a blog by myself. After a weekend of work, I can say that the whole process went super well, since Hakyll is already serving this blog from AWS.

I guess the best documentation for this is the code I produced, which you can find in my Github repo. The repo is basically what hakyl-init generates plus a provision directory with Ansible scripts. There is also a Vagrantfile, which I use to test everything on VirtualBox, and a decomputed.json Packer script which generates the AMI I use to instantiate my blog on AWS.

These provisioning scripts serve a simple purpose - to allow me to recreate my blog on any machine should I need to do it. The provisioning scripts roughly do the following:

  1. Installs some base software;
  2. git clones this repo;
  3. Calls hakyll build;
  4. Sets up and enables nginx;
  5. Sets up and enables a systemd timer to update the blog periodically.

With this in place I can just fire up an EC2 instance from my AMI and I’m all set. There’s still a few improvements and tasks left to do, like:

but now that I have this infrastructure, all of this work can just be done on top of what I built.