Bloomr.SG 2.0

Yesterday marked another important date for the team at Bloomr.SG. 2 whole years since our official launch. When around 3 years ago, the then Chairman of the Mediacorp Board, created a challenge to…

Smartphone

独家优惠奖金 100% 高达 1 BTC + 180 免费旋转




Agenda

disclaimer : all my writings, opinions and thoughts are mine.

In this post we will see how to securely host your website on Amazon Web Services (AWS) for Free in a production ready environment using CI/CD.

Fully Serverless : you won’t have to care about servers meaning that we will only use managed AWS services with all the underlying infrastructure to be managed by AWS.

We will do it in two ways :

I assume you already know a bit about :

If you’re familiar with AWS and Cloudformation just go the last section and get the templates to quickly launch it on AWS.

If you’re new to AWS the manual steps will help you understand what’s going on under the wood but still you should use the AWS Cloudformation templates of the last section in order to implement the infra for your Website. It is best practice (reasons explained in last section).

You want to publish your website while maintaining costs as low as possible but with :

In our architecture we have a CI/CD pipeline with 3 steps :

We will serve our website from Cloudfront for security and performance reasons instead of serving it directly from S3.

Cool feature on AWS : you can get free SSL certificate while using AWS services in order to serve you website using HTTPS.

Before getting our hands on, let’s breakdown each components in order to understand what we’re doing.

AWS Codecommit

If you’re familiar with GitHub then you know what is AWS Codecommit :
It is our source code repository where we will store our website code.

It uses Git, the famous free and open-source version control software.

Of course, if you prefer you can use Github instead.

AWS Codepipeline

What is a CI/CD pipeline ?
CI/CD is a DevOps practice which stands for Continuous Integration / Continuous Deployment.

Continuous Integration :
As you may already know, after deploying your website into production you will need to make some changes or updates on it : this is code integration.
Of course, you don’t want to achieve that manually since it would be source of potential errors. Plus, what if you have hundreds of code changes ? It would be a waste of time. Automating integration continuously is what we call continuous integration.

Continuous Deployment :
When your code is changed or updated then you need to rebuild it and to deploy it to your server. Again, we want to automate this process and not to achieve that manually but in a continuous and easy way.

In some cases, CD stands for Continuous Delivery : when you need human verification because of your company organization or processes or compliancy requirements. In that case, the pipeline delivers code to a human validator who manually validates the code before the pipeline continues to the deploy stage.
You can also leverage “pull request” functionnality in Codecommit to achieve code validation.

AWS Codepipeline will help us achieve automation. It will orchestrate our pipeline :

AWS Codebuild

It is a managed service meaning you won’t have to care about servers or any infrastructure. You choose which type of environment you want and configure the commands expected to be executed by these AWS managed virtual machines.

AWS S3

We will store our website code in an AWS S3 bucket with access only from our Cloudfront distribution.

We can serve our website from S3 but as of today we cannot use HTTPS with S3 alone but only with coupling S3 and Cloudfront.

The SSL certificate will bee freely provided by AWS ACM.

AWS CloudFront

It is the CDN service of AWS (Content Delivery Network).

Few reasons for using a CDN :

CDN in a very simple words : todays’ internet works well thanks to CDNs by bringing content closer to the end user which is broadly used by video streaming providers (Netflix, Youtube, x industry).

GoHugo is a static website and blog generator.
You can use existing templates (Themes) or build your own Theme from scratch.

Then you can test it on your local laptop by using the following command :

Of course, in order to deploy it in a Serverless production environment we will not serve it from a webserver like we just done on our local laptop but we will use a hugo command to build and package a static site to be hosted on AWS S3.

In this section I will go through the steps to manually implement the architecture.

All steps will be through the graphical AWS console, then you need to login in yours.

Go to Codecommit and create a new repo and enter a name :

Optionally, you can use AWS’s IDE (Cloud9) through your web browser to avoid all the steps in the documentation since it is natively integrated with AWS products.
Be careful of the costs of Cloud9 since behind the scene it launches an EC2 instance : there is an option in the initial Cloud9 setup to make it sleep after 30 min inactivity.

Go to your repo and copy the HTTPS URL on the top right corner hit “Clone URL” :

In your terminal enter the following command in the folder where you want to have it :

In my case :

Copy paste your website code in the repo you just cloned.
In my case, I copied the GoHugo code from the folder “QuickStart” created in the previous section into “example-repo” and then :

If you open the AWS Codecommit console (UI) then you will be able to see the code you just committed from your local IDE to Codecommit.

You need a build project in AWS Codebuild in order to build the Hugo website.

Normally you do it on your laptop when you Dev. However if you want a clean, secure and scalable production build environment Codebuild is a perfect fit.

You could launch a server through an EC2 instance but you would have to manage everything (security, scalability, resiliency, availability, patches etc).
As a Dev you want to avoid these SysOps headaches and take great advantages of AWS managed services very scalable, elastic and secure.

In order to create a build project through the console, go to Codebuild and hit “create build project” in the top right corner :

Then, enter a project name and leave blank the rest of the section :

Scroll and fill the next section (source) by selecting your Codecommit repo (“example-repo” in my case) and branch (“master” in my case) :

Scroll to the next section and configure the image to be used to launch the underlying EC2 instance (server).

Don’t panic ! It is a managed service, but yes, you still need to choose which kind of machine you want because you’re going to give some commands to be executed on that machine. Obviously, if you’re using Windows the commands syntax would be different from Linux that’s why they ask to choose.

Let’s configure it as below and leave the rest as-is :

Then scroll to the next section and copy the code below (I will explain later what it is doing) :

Then paste the copied code as below (click on switch to code editor to display full input) :

Let’s understand what’s going on the code you just pasted :

Our website final packaged code will live in a S3 bucket.

Let’s create it, go to AWS S3 console and hit the “create bucket” button :

Go to the “Block Public Access settings for this bucket” section and uncheck all boxes :

We uncheck all because we want public access to our bucket and Cloudfront that we will configure later will need access to this bucket for configuration.

Bucket policy is also needed to allow public access on our website.

Below is the JSON code for the policy to be pasted but make sure you replace with your bucket name.
It will allow the GET HTTP method from any public IP address (0.0.0.0/0) on all objects inside the bucket. You can customize it if your project has specific requirements (example you want to restrict access to a specific IP prefix that you own).

After replacing with your bucket name, paste it as below and hit “save” :

Click on your newly created bucket and go in properties tab, scroll down to “static website hosting” and hit “edit” button :

Check “enable” and “host a static website” .
Fill the default home and the error filenames respectively with “index.html” and “error.html” as below :

Go the Codepipeline and hit “create pipeline” :

Fill your pipeline name and leave the rest as-is :

Add Codecommit as your source stage and select your repo and your branch name, if you’re using Github then configure it accordingly :

Hit “next” and add a name for your project build as below and hit “next” :

Enter your target bucket name you previously created and hit the “extract file before deploy” box in order to unzip the file before putting it in the bucket and hit next :

Once you finished, go to Codepipeline and check the status of your pipeline, after a while it should be all green meaning that your code has been successfully deployed to your S3 bucket :

Now you should be able to browse to your website from the S3 URL (“bucket website endpoint”) provided in the “properties” tab in “Static website hosting” section at the bottom :

Your website is served from S3 but this is not what we eventually want ! We will modify it later. It was to show you that you can achieve hosting on S3 without Cloudfront.

On AWS console go to Route 53 and register a domain, enter all the contact infos and complete all the steps and make sure the enter valid email you have access to :

Go to the email address you entered and click on the validation link. If you do not click then the domain will be stuck in the pending requests.

Go to AWS Certificate Manager (ACM) and register for a new certificate for your domain name. Make sur to add a wildcard before your domain in order to be able to use the certificate for all subdomains of you apex domain thus avoiding creating multiple certificates.

Choose DNS validation and hit next :

Refresh the page and go to the pending certificate and hit the “create Record to Route 53” button below :

Hit “next” wait a couple of minutes and you SSL certificate is now issued.

In AWS console, go to Cloudfront and hit “create distribution” :

Be sure to check “redirect HTTP to HTTPS and leave the rest as-is :

Then in the next section :

Go to cloudfront and make a copy of the distribution domain name. Then go back to your AWS S3 bucket in the properties tab and scroll down to “Static website hosting” and hit “edit”.

It has been a very long journey as you can see, if you’re still there lol.

We’ve been through many manual steps which can involved many human errors. And what if we want to reproduce this in another AWS region for better resiliency or for another customer or multiple times ?

Fortunately for us, AWS has an amazing tool to help us avoid such errors and pain in order to automate infrastructure deployment : AWS Cloudformation.

AWS Cloudformation relies on templates : you describes what you expect Cloudformation to deploy on AWS for you in YAML or JSON files.
This is commonly called Infrastructure As Code (IaaC) as you may already know.

In order to deploy all the previous manual steps we will do it two steps:

You will land on this page and hit next :

If you don’t have a hosted zone, meaning that your domain name isn’t registered with AWS route 53 then you need to change and customize the templates of the Github which is not part of this tutorial.
You should probably consider to transfer your domain to Route53 because it gives you very cool and advanced features : you can split the traffic to different versions of your website with blue/green deployment which I’ll cover in an other article.

Fill all the fields with your domain name (in my case “samy-fadel.com”)and copy your hosted zone from route 53 :

Hit next until the end leaving default values for the rest and to hit “create stack”.

Wait a couple of minutes (10min in my case) and that’s it.

At this stage you could manually upload your code to the newly created S3 bucket and have your website up and running. However, it would be a pain to update and manage code…

Next section is there to fix this and let you benefit from CI/CD and update code easily and frequently !

On your laptotp create an empty file called “template.yaml

Copy the below code and paste it in your new empty YAML file in order to upload it in Cloudformation :

Cloudformation will ask you to enter the parameter names : be sure to fill the bucket name with the bucket created in step#1.

That’s it your infra is up and running !!

We learned many things here we can re-use for more complex Apps.

In theory, you will never get charged for what we deployed, even outside of the AWS free tier period, except if :

Your website benefits from professional SLAs such as the legendary 11 nines of S3's durability and a CI/CD pipeline to cleanly release code and updates.

In the next article, I will add a blog to our website sample and we will see how to leverage AWS services to build a fully cheap Serverless CMS instead of using Wordpress.

I will also write an article on how to add blue/green deployments to our architecture in order to easily and securely control how you release changes to your website with multiple versions up and running simultaneously.

Add a comment

Related posts:

A Tale of Two Elections

What does it mean that I went from gloating after the 2004 presidential election to despairing when Trump won in 2016?

Do You Have to Pay for ChatGPT?

ChatGPT has revolutionized the way people interact with AI by enabling natural language conversations and providing valuable assistance across various domains. It has become popular among…

The Truth Will Set You Free

Confucius and many other ancient Asian sages proclaimed the immense negative effects on one’s own life and longevity because of the use of lies, or what roughly translates to “the twisted tongue.”…