How to set up a blog in Microsoft Azure using Ghost. Optionally, add on a custom domain name and SSL encryption using Let's Encrypt.

One of the biggest challenges I have been facing recently is deciding where I am going to store content. For work I have been using Microsoft OneNote fairly extensively. At home my wife and I were using it for a bit as well when we were trying to create to-do lists. But it became a bit cumbersome and we switched over to Google Keep (mostly for those lovely honey-do lists). Both applications work great for synchronizing lists and notes with our various devices. But what happens when you want to share things with the public?

WHY GHOST?
I was looking for an easy-to-manage solution for blogging and thought: "oh, I'll just go and set-up a WordPress solution using Azure's PaaS (platform as a service) Wordpress solution and let it run on Linux." Sounded great. Until I realized that I don't know PHP and administration would be a bit cumbersome. So, I went looking for a solution and stumbled upon Gareth Emslie's post about running Ghost Blog in containers on Azure App Service. Awesome. Just a few clicks and the blog was up and running.

SETUP
RESOURCES
Gareth Emslie: How I am running my ghost blog on Azure

PREREQUISITES
I am not going to reinvent the wheel here as Gareth covers everything quite nicely in his post. If you want to simply get something up on the Web all you need is an Azure Subscription, a Storage account and Docker running on your local machine.

That being said, because I like the additional control, there are just a couple extra considerations that I would like to bring up.

First, hosting Ghost blog in a container on Azure is going to come at a small, but non insignificant, price. If you want a custom domain name you'll need a "Basic" tier App Service and this is going to set you back $38 at the time of publication. If you don't need a custom domain name you can use Azure Container Instances for a song (back of the napkin math says around $5). For your container registry you have three choices: you can use Azure Container Registry (Basic tier is fine at $5/month), Docker Container Registry or build your container dynamically by pulling from Azure DevOps or GitHub. My setup with Azure App Service running Standard Tier (for $71 ), an Azure Container Registry on Basic Tier ($5) will set me back approximately $76 a month. Oh, and it will be able to host a slew of other containers. Wicked cool.

Note: The first tier for Web Apps where you will get a custom domain, and thus SSL, is in the "Basic" tier.

Second, with Azure Container Registry CI/CD is going to be built in for me. I'm using Azure DevOps to host my repository. The deployment will happen whenever I push an update to the container in my registry.

Third, do you want to be able to control your infrastructure for your blog in a programmatic way? In this case you can use Powershell, ARM Templates or the Azure CLI to build out your Web App, Storage and other components for you on demand.

CUSTOM DOMAINS
Note: The first tier that will allow you to have a custom domain is currently the "Shared" tier. If you're hosting in the "Free" tier you will not have access to the features from here on out.

For this blog I wanted to go a few steps further and host it under a custom domain. First, I registered the custom domain. Second, I chose an appropriate pricing tier for my Web App in Azure. However, if you've already chosen a tier for you Web App don't worry, you can easily change the setting in the Azure Portal.

Setting up the custom domain was easy. I want to host the blog at the site you're viewing it at. I just had to set up a couple "A" records and "TXT" records with my domain registrar and configure a couple settings in the Azure Portal under my web app. It's all pretty straight-forward.

Mapping a Custom Domain Name

SSL ENCRYPTION
Note: you will need to set up your custom domain before you get to this part. Otherwise you cannot set up SSL. Additionally, as of publication you will need to bring your own SSL certificate with you. Linux App Services currently do not support webjobs so the following will not work. However, I am preserving this from the original post as it is very helpful for setting up Let's Encrypt in an App Service.

This was actually the tricky bit. Troy Hunt wrote a great article about using Let's Encrypt as an App within your Azure subscription.

Resources:

-Troy Hunt: Everything you need to know about loading a free Let's Encrypt certificate into an Azure website

-Azure Docs: Setting up Azure AD

-Setting Up Let's Encrypt for Ghost

It is a bit involved as there are a few steps that you will need to follow in sequence. Again, I'm not going to rewrite his post but here's a couple gotchas that arose while I was adding the SSL certificate from Let's Encrypt:

1 When you create your app in Azure AD (called Let's Encrypt) Troy's post mentions a "clientid". This id has changed names to be called "Application ID" and is a Guid. When you create the ApplicationId you will also need to create a "Secret" (this is called either an application secret or a client secret, these terms are synonymous). You'll want to take note of the Guid and the secret and them to notepad.

2 When you create your keys for your Let's Encrypt app, I created two in case I need to rotate them, you will want to take note of these and copy them to notepad.

3 In the Azure Portal when you are looking for your "Tenant Name" you can find this by hovering over your photo in the upper right hand corner of the portal. This is no longer displayed by clicking on your photo and you can't copy/paste it. In fact, the tenant is listed as "Domain". You will need to take note of this and copy it to notepad.

4 Once you have added your keys and secrets to you Web App you will need to open Kudu and update your Web.config settings under "site/wwwroot/Web.config". See Setting Up Let's Encrypt for Ghost towards the bottom for the updated settings you need to paste into Web.config.

CONCLUSION
That pretty much wraps it up.

If you have any questions, need any clarifications or just want to report back on your successes please leave a comment or send me a Tweet.