I finally got fed up, I was suffering some serious “blogengine/design paralysis”. I didn’t seem able to decide on which engine and framework I should use for my own blog. But probably more important, I didn’t know what topics I should focus on. Enough is enough, I picked Hugo for static website generation, Docker to run the whole thing in a container and I just picked a theme that looked the best to me.

To prevent this blogpost to be a “Hey, here’s my brand new blog”, I’ll just tell you how I set this whole thing up, and what kind of workflow I’m using right now.

tl;dr

Creating a new blog on Medium or Wordpress is easy. But hey, where is the fun in that? I also took this route to learn some things about Docker, Docker Compose and Docker hub, Letsencrypt, and what it’s like to use a static website generator.

The key take aways

  • Using Markdown, a static web generator and git really translates into a Content Management System for Developers
  • Learning Docker is all about doing; a fairly simple thing as running a blog in a Docker container already gave me some a lots of “AHA” moments.
  • Since the introduction of Letsencrypt you really have NO reason to skip https support.
  • Open-source software once again proves that it can create magic
  • After setting everything up, I immediately thought that this could be automated a lot more. This is far from a turn key solution. See how you can deploy a static site with a press of a button at Staticgen.
  • Disqus, Google and Gravatar are all evil. Run your own, or die trying ;)
  • Writing good content takes time
  • 191.96.249.42 - - [02/Feb/2017:15:06:52 +0000] “GET /phpmyadmin/scripts/setup.php HTTP/1.0” 404 169 “-” “-”… No sorry .php is not in the office today. Try https://www.phpmyadmin.net/ maybe they can help you out. G’day.

Why go static?

The reason main reason I wasn’t going with just starting a blog on eg. Wordpress.com, Medium or Blogger (are people still using Blogger) is that I wanted total control over my own content. And on top of that, I wanted it to run as “platform agnostic” as possible, in other words the content shouldn’t be tightly coupled to the platform or software that I use. For a .NET fanboy like me, going the .NET Web Application + Database combo route would be the obvious choice. But that’s something within my comfort zone, and I wouldn’t really learn something new from it.

These days all the cool kids go static with their blogs. Static meaning that the site is served straight from the filesystem, no dynamic content is being served from the database or is generated on the server. To create a blog the static way, you use a static website generator, like Jekyll, Hugo or Hexo to create their blogs. Creating content in Markdown and using git as content management feels a lot more awesome to me. And if I decide to switch to another blog engine or platform, I think by having my content written in Markdown is as future proof as it gets. I can host the site virtually anywhere I want. No database, no server side mumbo jumbo, just plain html+css+js served by a web server. If I want to host it on a el cheapo shared server, I can do that. If I want to host it on my own dedicated server, I can do that too.

I run a VMWare Esxi Lab at home on a home made “whitebox” server. This helps me with trying out new software or operating systems quite easily and on top of that I get a little bit of experience with running Hypervisor software. This actually is valuable in my day to day job; it helps me to understand what the “ops guys” have to deal with. And at home I can run stuff like Plex for serving media, play with Docker, or investigate a build/deploy configuration with Teamcity & Octopus. If you’re very passionate about software development and new technology in general, I really recommend you to give VMWare Esxi, Hyper-V or any other Hypervisor a try.

Ok, nice. But how did you make that static thing happen?

So my starting point for setting up this blog is a Ubuntu Server virtual machine running on Esxi instead of on bare metal. But you might as well spin up a VM in the cloud or run it on a Raspberry Pi.

Ingredients for the best blog evah no seriously this is the best blog evah in the history of the internetz

  • Ubuntu Server 16.10
  • Docker 1.13
  • Docker Compose
  • Hugo
  • Github Gitlab
  • Nginx
  • Letsencrypt/certbot
  • Tranquilpeak theme
  • Cool content
  • Unsplash and their awesome pictures

So as stated above, I started with an Ubuntu Server. And for people that are unfamiliar with Ubuntu, the Server edition is the one that runs without an ui and is optimised for server workloads. Off course it’s important that this server should be accessible from the web, and both port 80 and 443 should be “opened”.

The instructions to install Docker on Ubuntu can be found here. Repeating those instructions here would only lead to outdated information. The same for the Docker Compose instructions. We also need Docker Compose because the site will be served by two containers, and it’s a best practice to run a compositions of containers with Docker Compose. Instructions to install Docker Compose can be found here.

Static flow with Hugo, Yo

I installed Hugo, a static site generator based on go-lang on my laptop. On a Mac this is quite easy. When you have brew installed, and what sane developer hasn’t, you simply execute brew update && brew install hugo from the commandline. The installation instructions for other platforms can be found on the Installing Hugo page.

Now we’re all set to create content using Hugo. That’s actually the hard part ;) I chose to use the Tranquilpeak theme because it looks nice to me. But there are a lot more themes which you can use with Hugo, and of course you can create your own. I use Visual Studio Code to edit the Markdown files, and the VS Code Extension Hugofy that makes it a bit easier to create new posts, and start/stop de Hugo server. For new blog posts my workflow now looks like this : write markdown, commit & push, and SMILE!. You gotta love that simple yet effective way of blogging.

Docker is the name, containers are the game

The next part is quite cool. I wanted my workflow of writing new blogposts and publishing it on the web to be easy. At the same time I wanted to have the feeling I can control every part of it. Because I have been playing with Docker for a while now, running the static website from a Docker container was high on my list. So the first thing I did, is Google with the keywords hugo docker nginx letsencrypt which lead me to the this Docker image handcraftedbits/nginx-unit-hugo. It serves the static site using Nginx, and as a bonus it also handles the https part by using a Letsencrypt certificate. And what’s also very convenient is the fact that the container can be configured to listen to a webhook from Github. So after a I commit and push the content, the container automatically updates the website. Pure win!

Own your space on the Web, and pay for it. Extra effort, but otherwise you’re a sharecropper.

Initially I used a Github repo for the content, but I do not have a payed account so I can not create a private repo. I know it’s a lot more open if I put the source for the blog in a public Github repo, but then my drafts would also be visible to the public. And the way I write, I really don’t think it would be meaningful for other people to read my drafts, and on top of that the “suprise factor” would also be gone. That’s why I have chosen to use Gitlab which I have running on my own server, that way I feel like I’m in control again and really own my content. The only issue I had is that the webhook that’s used in the Docker container is not compatible with Gitlab. So I forked the source for the original Docker image, changed a webhook config file, and then built the image and pushed it to Docker Hub: saberone/nginx-unit-hugo-gitlab

You want control? Buy a domain and blog there.

The Docker image expects, at least to my understanding, you to have an initial letsencrypt certificate setup. On Ubuntu I used certbot. Of course the domain name that you want to use should point to the machine you’re using to run the Docker container. I have registered mine, because I’m cool like that ;) Then you run the certbot tool from commandline and answer a couple of questions, and you get a shiny new certificate that you can use for an https endpoint. As an extra you should also generate a so called “2048 bits dhparam.pem” file, this gets you a nice A+ rating on SSL Labs.

Docker compose

Next thing I did is create a docker-compose.yml file with the following content:

version: '2'

services:
  data:
    image: handcraftedbits/nginx-host-data

  hugo:
    image: saberone/nginx-unit-hugo-gitlab:latest
    environment:
      - NGINX_UNIT_HOSTS=blog.mydomain.somewhere
      - NGINX_URL_PREFIX=/
      - HUGO_GITLAB_SECRET=verybigsecret
      - HUGO_REPO_URL=https://gitlab.onpremise/saber/blog.git
      - HUGO_THEME=hugo-tranquilpeak-theme
      - WEBHOOK_VERBOSE=true
    volumes_from:
      - data

  proxy:
    image: handcraftedbits/nginx-host
    links:
      - hugo
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - /etc/letsencrypt:/etc/letsencrypt
      - /home/saber/certs/dhparam.pem:/etc/ssl/dhparam.pem
    volumes_from:
      - data

As you can see the running container will listen to port 80 and 443, and if a visitor opens the site using the regular http, he or she will be redirected to the https url. Then I did a docker-compose up -d . in the same folder as the docker-compose.yml was, and Unicorns appeared!

It’s all about the content

Ok all that tech to be able to create a blog is cool. But in the end it’s all about the content off course. I mentioned a couple of times that I wanted to control my own content and especially how and where it’s being presented. One of the “bonuses” you get when you use a “free” blogging platform is that the visitors to your site are confronted with obnoxious ads. Yes, I know, the internet isn’t really free. And the ads help to pay the bills. But advertising has gotten way out of hands. When I use gravatar for my picture, Disqus for commenting and Google analytics for tracking visitors, I’m getting quite a few trackers. Especially Disqus brings along many of its tracking friends.

Now with 14 trackers for free!!! Now with 14 trackers for free!!!

So I disabled Disqus, until I find a good alternative that I can host on my own server and I replaced the Gravatar image with a self hosted image. But Google analytics I’m keeping for now. As with Disqus, I’m looking for a good alternative that gives me insights on how my site is doing.

Now with the hurdle of choosing the right tools to get the job done out of my way, I’m all set to create some nice and delicious content on an open-source self hosted platform. Awesome!!!111ONEONETWO!!!