Why I chose Zola to build this site

2023-11-29

My trysts with blogging#

I’ve been writing blogs on and off for a few years now. Like most people, I began my journey via a platform that had a low barrier to entry, namely, Medium, because I could just get to writing straight away, and I didn’t have to worry about hosting, security, or any of the other things that come with running a website. I just wanted to write good technical content, and Medium was a good place to do that a few years ago.

Fast-forward to today, and my thoughts have evolved with the changing landscape, not to mention that my tech skills are way better than when I started off. 😅

Why do I blog?#

This is a good time to bring up some @karpathy philosophy:

Point #1 deserves a deeper exploration and a blog post of its own, but with regard to blogging, I think point #2 is very relevant, and in my view, leads directly to point #3.

It’s hard to explain a concept to someone else unless you understand it at a deep enough level yourself. But, you can’t really understand something well enough unless you’ve had to explain it to someone else. How does one break this virtuous cycle? I think the answer is in writing, or blogging, about the things you’re learning.

How does blogging lead me to point #3 in the above Tweet? I write primarily for myself, and then when I look back at how far I’ve come, I end up comparing myself only to younger me, and never to others. Deep, indeed!

Why not Medium?#

When I was writing on Medium, I found myself constantly worrying about how to stand out in the ocean of existing content already on there. This is a natural consequence of writing on a platform that’s designed to get you more views, and more clicks, and more engagement. I found that this was taking away from the joy of writing in itself.

We now live in a world of hype and self-promotion – at least, for those of us in the A.I. and software engineering space. Platforms like Medium have been inundated with content that’s just trying to grab the reader’s attention, garner clicks, and include every buzz word in the modern tech lexicon. The content out there just looks the damn same as everything else.

Add to this the fact that half the writers on Medium are putting their articles behind paywalls, and you have a recipe for disaster. I’m not saying that writers shouldn’t be paid for their work, but I think the paywall model that Medium is pushing is fundamentally flawed.

I’m not going to pay for a subscription to a platform that has a ton of content that I don’t care about, just to read one article that I do care about. I’d rather pay the writer directly.

Why not Substack?#

Substack is fundamentally a newsletter site, not a blogging platform. It’s designed to encourage the reader to subscribe to a writer’s newsletter, and receive updates via email. Not only this, but there are also very limited features for things I care about to write a technical blog, such as code syntax highlighting, LaTeX support, and so on.

Oh, and just like Medium, every Substack blog looks the same, visually, which again makes it hard to discern the work of one individual writer from another, unless you subscribe to a ton of newsletters.

Why I self-host#

Below, I list some of my fundamental ideas about blogging and open knowledge-sharing.

  • Knowledge that I gained from the public domain should, ideally, be shared back within the public domain – I believe this is what advances human knowledge and understanding.
  • Reading and writing content should, to a certain degree, be a personal experience and not a cookie-cutter one.
  • Content should appear in a format that’s easy to read, and not be cluttered with ads, pop-ups, and other distractions.
  • To stand out in a sea of otherwise similar-looking content, you need the ability to customize aspects of your blog, such as the layout, the fonts, the colours, and so on.

I’ve been thinking about these ideas for a while now, and the only thing preventing me from going all in was the perceived difficulty of setting up a static site.

Static vs. Dynamic sites#

Anyone who’s read anything on Medium will have noticed the dynamic nature of how it shows content. A dynamic website loads pages on the fly, typically relying on an underlying CMS (Content Management System) to store and retrieve content from a database. This is in contrast to a static website, which is just a collection of HTML, CSS, and JavaScript files that are served as-is to the user.

Static sites are faster to load and, in my view, provide a much smoother reading experience than dynamic websites. For blogs, where the primary medium of interest is text, using a static site seems like a no-brainer. However, it does require some understanding of the modern web, including HTML, CSS and JavaScript.

Static Site Generators (SSGs)#

Of course, nobody in their right mind would want to put in days of work to structure their website. This is where Static Site Generators come in.

If you’ve ever taken a good look at HTML, it should be clear that it isn’t fun to write it all by hand. Therefore, we invented the Static Site Generator (SSG): a program that takes an HTML template and some text in a more human-friendly form (usually Markdown), and mashes them together, yielding a servable HTML file1.

1

Marcus R.A. Newman, in the Prefetch blog

There are a ton of SSGs out there, including Jekyll, Hugo and Pelican. The main benefit of using an SSG is that it allows you to write content in a human-friendly format, such as Markdown, and then generates the HTML files prior to deployment. All it then takes is a bit of tweaking the CSS and adding some minimal JavaScript to get the static site up and running.

What is Zola?#

Zola is:

A fast static site generator in a single binary with everything built-in. This tool and the template engine it is using were born from an intense dislike of the (insane) Golang template engine and therefore of Hugo that I was using before for 6+ sites.2

2

Creator of Zola on their GitHub repo

Moving on from Hugo#

Hugo, the world’s most popular SSG written in Golang, was my first choice until recently. However, once I discovered Zola, an equivalent SSG written in Rust, I was immediately hooked. Just like the creator of Zola mentioned, the main issue for me with Hugo is its underlying Go template engine, which made it immensely difficult to customize the look and feel of a theme I liked. I found myself spending hours, or even days, trying to figure out how to get my site to look the way I wanted it to, rather than actually writing content.

Although Hugo is hugely popular and there’s tons of examples online, it was still proving too hard for me to learn how to effectively use its templates and short codes. Zola addressed all these concerns, and more. Within a few days of looking up the documentation on Zola’s template engine, Tera, I was productive enough to get my site’s customizations up and running.

The anatomy of a Zola site#

A Zola site is just a collection of files and folders, with a specific structure.

.
├── config.toml
├── content
   ├── about
   │   └── _index.md
   ├── posts
   │   ├── post-1.md
   │   ├── post-2.md
   │   └── _index.md
   └── projects
   │   └── _index.md
   └── _index.md
├── sass
   └── main.scss
├── static
   ├── font
   │   └── custom_font.woff2
   ├── img
   │   └── icon.png
   └── js
       └── main.js
└── templates
    ├── base.html
    ├── index.html
    ├── page.html
    ├── post.html
    └── section.html
  • config.toml is the main configuration file for your site. It contains information such as the site’s title, description, the theme to use, and so on.
  • _index.md at each directory is a special file that tells Zola to generate a page structure based on the declared front matter.
  • content is the folder where you’ll write your content. Each file in this folder is a page on your site.
    • Zola allows the concept of section and page to keep things clean and organized
  • sass is the folder where you’ll keep your CSS stylesheets. Zola uses the Sass CSS preprocessor, which allows you to write CSS in a more human-friendly way.
  • static is the folder where you’ll keep all your static assets, such as images, fonts, and JavaScript files.
  • templates is the folder where you’ll keep your HTML templates, which can be customized via shortcodes
    • Zola uses the Tera template engine, which allows you to generate HTML pages via a template language very much like Python’s Jinja2.

Steps to setting up a Zola site#

If you’ve never set up and deployed a static site before, don’t worry! It’s not as hard as it sounds.

Install Zola#

Zola is a single binary, which means you can just download the binary for your platform. I’m on Mac, so I just used Homebrew to install Zola:

brew install zola

Navigate to an empty directory and type in zola init to initiate a base Zola site. This will create a config.toml file and a content folder.

Define your requirements#

For me, these were the main requirements I had in order to write productively. Spend a bit of time thinking about what matters to you, and define a list accordingly!

  • LaTeX math equations
  • Code syntax highlighting
  • Customizable themes and layouts
  • Table of contents
  • Footnotes and references
  • Callout boxes (info, warning, etc.)
  • Comments
  • Privacy-focused site analytics

Pick a base theme#

Zola has an excellent list of starter themes that you can choose from. For this site, I chose the Serene theme and then customized it to my liking. Always pick a theme that gets you most of the way towards the requirements you defined above – the styles, layouts and templates can then be customized to meet all the requirements later on.

Understand the theme’s structure#

Spend a bit of time on the theme’s documentation and examples to understand which files control the layout, styles and fonts. In my case, I found that the templates folder contained the HTML templates that had Tera code in them, and the sass folder contained the Sass CSS stylesheets. Once you tinker around with them for a bit, it becomes clear how to make modifications to the theme.

Customize the theme#

Decide on what features matter to you the most, and begin tinkering with the stylesheets, templates and configuration files to get the theme to look the way you want it to. This is a time-consuming step up front, but with Zola, I found this to be much more intuitive and fun than I did with Hugo. As I mentioned earlier, within a few days of tinkering with the Tera template files, I was able to be productive enough to get the first version site up and running on my local machine.

Write content and test locally#

Navigate to the content directory and begin writing a post in Markdown. You can use the zola serve command to start a local server that will serve your site on localhost:1111. You can then navigate to localhost:1111 in your browser to see how your site looks. This is a great way to test your site locally before deploying it.

Deploy your site with a “Hello World!” post#

To get the site up and running on the web, you’ll need to deploy it somewhere. I chose GitHub Pages because it’s free and easy to set up right within the source repo. I also chose to use a custom domain name, which I purchased from Namecheap, but this step is totally optional – GitHub Pages allows you to host the page on https://myusername.github.io as well, for free.

How to deploy?#

Netlify or Vercel#

The easiest way to deploy a Zola site is to use a service like Netlify or Vercel. Both allow you to deploy static sites on a free tier, and directly connect to the source repo in which the code is based. I haven’t used either of these services, but the Zola docs contain good instructions for them.

GitHub Pages#

A slightly more involved (but totally free) approach is to use GitHub Pages, which allows you to host static sites right from your GitHub repo. The only caveat is that if you want to host a site without specifying a custom domain name, it has to have the same name as your GitHub username. For example, this site is based in the thedataquarry GitHub organization, so the site is available at the following URL: https://thedataquarry.github.io.

To deploy a GitHub pages site, it helps to have some basic familiarity with GitHub Actions. GitHub Actions are a way to automate tasks within your GitHub repo, such as running tests, building and deploying your site, and so on.

Set up a GitHub Action#

Create a directory called .github/workflows in the root of your repo, and create a file called build.yml in it. This file will contain the instructions for GitHub to build and deploy your site. This site uses the standard Zola GitHub Action, which is available here.

build.yml
name: Deploy Zola site to Pages

on:
  push:
    branches:
      - main

jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
      - name: Checkout
        uses: actions/checkout@v4
      - name: Build and deploy
        # v0.17.2 didn't work for me for some reason, so I used v0.17.1
        # master also worked: shalzz/zola-deploy-action@master
        uses: shalzz/zola-deploy-action@v0.17.1
        env:
          PAGES_BRANCH: gh-pages
          TOKEN: ${{ secrets.GITHUB_TOKEN }}

Once a Markdown file has been written and pushed (along with any other changes to other files) to the main branch, this action triggers and builds the site on the gh-pages branch.

Note

The above build.yml just builds the site on the gh-pages branch. To make it accessible on the web, navigate to the Settings > Pages section of the repo and set the following:

  • Build and Deployment:
    • Source: “Deploy from a branch”
    • Select the gh-pages branch

This will host the site and make it accessible on https://myusername.github.io.

Optional step: Set up a custom domain#

It’s possible to point the deployed site on https://myusername.github.io to your own custom domain. Assuming you have a domain name purchased on Namecheap, you can follow the instructions here to set up a custom domain.

In my case, I navigated to the advanced DNS settings for my domain on Namecheap, and added the following records:

I created the list of A records to point my apex domain to the IP addresses for the GitHub Page, as per the docs. Note the CNAME Record on the last line (this is important). On the Zola side, I simply create a file called CNAME in the static folder, and add the following line to it:

thedataquarry.com

Conclusions#

In this post, I covered some of the basics of static sites, SSGs, and how to deploy a Zola site via GitHub Pages.

I hope this post inspires you to setting up your own static site and get to writing! Putting down your thoughts and learnings in writing is a great way to push your boundaries, contribute to the open sharing of knowledge, and to make a mark on the world, no matter how small. Good luck on your journey! 🚀

Code#

The code for this website is available here. If you like this template, free to use it and begin tinkering with your settings, and consider providing attribution to the original author, just like I did. 😄