If you’ve visited my blog before, you’ll notice that things look a bit different π I decided to swap from the old framework, Jekyll, and deploy Hugo. Thankfully, my workflow makes it simple to swap out the entire framework and keep my content structure same. If you’ve ever thought about running your own blog, I highly suggest this setup. It’s lightweight, simple, and nearly free! Let’s dive into it.
Overview
My use case for a website is simple: hosting a bunch of static content, e.g. HTML/JS, CSS, image files, etc. Traditionally, if one wants to host a website that involves setting up a webserver. Not too difficult but a running a server comes with it’s own set of challenges, not limited to:
β Software running on the server must be updated/patched regularly.
β Firewall rules/Network ACLs must be managed.
β Sudden spikes in user traffic can cripple the server, degrading the experience for users.
β Lastly; and more importantly, you are paying for a webserver regardless of if you have web traffic or not!
Introducing β¨Serverlessβ¨
Below is a diagram of all the moving pieces of the blog you are currently browsing

Seems simple, right? That’s because it is! Let’s get into some more of the technical details of each of these components.
Github
A platform we all know and love π. Github provides a beautiful frontend service that essentially facilitates access to the popular version control software, Git (plus some other Github specific features). What this means in practice is that I don’t have to maintain my own version control service, I can push my blog post content to a private repo in Github for free! This allows me to easily maintain a changelog of my blog β¨ Serverless β¨
Github Security Benefits
This wouldn’t be a security blog if we didn’t discuss any security concepts. Here’s a highlight of my favorite security features that Github provides:
- MFA on my Github account. This provides a 2nd barrier to entry should my complex passphrase be compromised.
- SSH key based access to the git repo that contains the blog source code.
- In addition, there is a strong passphrase on the SSH key being used! π
- Github Secrets: Store sensitive secrets here instead of in code (NEVER STORE SECRETS IN CODE). I.E., Github Secrets holds the credentials to authenticate and push the content to the backend S3 bucket.
Amazon Simple Storage Service (S3)
Amazon Simple Storage Service (Amazon S3) is an object storage service offering industry-leading scalability, data availability, security, and performance. Speaking of performance, S3 definitely will not suffer from the aforementioned spike in user traffic issue. Amazon S3’s performance supports at least 3,500 requests per second to add data and 5,500 requests per second to retrieve data1 π± Seems like more than enough for a personal blog. All that performance must come with a hefty price tag, right? My S3 usages costs me roughly $0.12/mo.
S3 Security Benefits
The S3 Security infographic can highlight all the features better than I can, but my favorite secuirty feature of S3 is how granular you can scope access to your bucket; even down to the specific bucket actions.
For example, the S3 bucket storing the static blog content is configured to only allow the Cloudfront distribution to retrieve objects; and only the configured Github user to push new content to the bucket. So useless you are the specific Cloudfront identity or Github, it’s a no go2 π« Have a look at the bucket policy yourself:
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "AllowCloudFrontServicePrincipal",
"Effect": "Allow",
"Principal": {
"Service": "cloudfront.amazonaws.com"
},
"Action": "s3:GetObject",
"Resource": "arn:aws:s3:::blog.medarkus.net/*",
"Condition": {
"StringEquals": {
"AWS:SourceArn": "arn:aws:cloudfront::ACCOUNT_NUMBER:distribution/E3GH09R6GYZ2LA"
}
}
},
{
"Sid": "GithubAction",
"Effect": "Allow",
"Principal": "*",
"Action": [
"s3:PutObject",
"s3:PutBucketVersioning",
"s3:GetObject",
"s3:GetObjectVersion",
"s3:ListBucket"
],
"Resource": [
"arn:aws:s3:::blog.medarkus.net",
"arn:aws:s3:::blog.medarkus.net/*"
],
"Condition": {
"StringEquals": {
"aws:username": "github-blog-user"
}
}
}
]
}
In addition to the security of the managed S3 service, there is MFA on the AWS account itself.
Cloudfront
Cloudfront does a lot of things but the easiest way to think of it is as a Content Delivery Network built for high performance, security, and developer convenience. What that means is that Cloudfront handles the messy details of pushing my static content out to the rest of the globe, and even intelligently caching it at specific edge locations (this speeds things up). Since the content you’re currently viewing is just sitting in an S3 bucket somewhere, Cloudfront allows you to view it in a sensible manner.
Cloudfront Security Benefits
As well as delivering my content, Cloudfront also provides security by protecting my blog from malicious activity like DDoS attacks, bots, and other nefarious intrusions. Not that there’s anything to compromise anyway π
Conclusion
So as you can see, β¨ Serverless β¨, or rather; managed services, take a lot of the pain away from managing your own infrastructure. This setup I just described allows me to focus on writing blog content and leaving the updating, patching, monitoring, and responding to the folks managing the services that power my blog.