In a previous article, I gave a glimpse into how we can use WordPress using various Amazon Web Services like EC2, VPC, etc. In this article, we will be setting up a similar environment without using the available AMIs for WordPress and MySQL database servers. Rather, we will be installing MariaDB, which is a community fork of MySQL, and WordPress onto AMIs with Linux as the base operating system.
We will also be looking into more services offered by AWS for networking like Route Tables and NAT Gateways.
Our main objective is to set up WordPress and MySQL on different AWS EC2 instances, by creating the following:
- Virtual Private Network (VPC)
- A public subnet (which has internet connectivity)
- A private subnet (which does not have internet connectivity)
- Internet Gateway for allowing internet access to the public subnet
- NAT Gateway for the private subnet
- Route Tables, which will be associated with the subnets
- Two AWS EC2 instances, with MySQL and WordPress, installed on separate instances.
Before beginning the setup, we need the following pre-requisites:
- AWS Account (Reference 2)
- Installation of AWS Version 2 CLI command (Reference 3)
- Installation of Terraform (Reference 4)
Writing the Terraform Code
To make the code easier to read and maintain at later stages, it is better to write the code for each resource in separate files, which can be later provisioned in the root module (often named as main.tf), by calling the respective resource module. By using input variables and outputs, we can write a basic framework of code that can be customized as per the requirements of the user. The directory structure I have followed is shown below. Note that the folder .terraform is created after executing
terraform init on the command line, and the files terraform.tfstate and terraform.tfstate.backup are created only after the successful provisioning of at least one of the resources. The file task4_key.pem is created if the key generation occurs successfully.
Each of the files we write will need to be stored in separate folders if we want to use them as modules. While it is possible to use a single directory to store all files, using separate directories for each file helps in creating modules that behave like molds which can be customized as per our requirements.
We begin by writing the code for the Virtual Private Network (VPC).
Next, we write the code for provisioning subnets. Even though we need two subnets (public and private), we just need one module which can be called as many times as needed in the root module (main.tf)
Then, we write the files for provisioning Internet Gateway, NAT Gateway, and Elastic IP. The Internet Gateway provides internet connectivity to the public subnet. The NAT (Network Address Translation) Gateway allows a roundabout way for the private subnet to access the Internet. The Gateway is designed such that any EC2 instances launched in the private subnet can connect to the internet, but instances from outside cannot connect to the instances in the private subnet. The Elastic IP is another service provided by AWS, which allows us to allocate a public IP to the NAT Gateway, which will, in turn, allow the instances of the private subnet to access the internet.
Next, we write the files for creating route tables and associating the route tables with the respective subnets.
To create EC2 instances, we need the respective security groups as well as a key that will allow us SSH access into the instance(s). Hence, we write the files for key generation (key.tf) and provisioning security groups (sgs.tf)
Finally, we create two files — one for the EC2 instance with MariaDB (sql_os.tf)and another for the EC2 instance hosting WordPress (wp_os.tf).
We then create a final file to link the MariaDB database with the WordPress we have hosted on the separate EC2 instance. To do this, we will need to login to the WordPress instance using SSH and finish the set up of WordPress as a whole. This is done using the null-resource provided by Terraform.
Once all the files have been written, we can create all the resources by calling the respective modules in the main.tf file. In this file, we can see that there are some variables used for user customization. These variables can be either declared directly in the root module or they can also be written in a separate file named variables.tf.
In the main.tf, the EC2 instances for both WordPress and MariaDB are launched using the Amazon Linux 2 AMI. This is to make the process of setting up WordPress and MariaDB easier (Reference 7,8).
Now, we can successfully create all the resources using the following commands, with the current directory set to the location of the root module.
terraform init #Used to initialize providers & modules being used
terraform plan #Performs a dry run to find errors
terraform validate #Checks for any syntax errors
terraform apply --auto-approve #Used to create all the resources
Once all the resources have been successfully created, we can begin the installation of WordPress by using the public IP of the EC2 instance where WordPress has been downloaded. In your web browser, type the following to begin the installation
<Public IP of instance>/wp-admin/install.php
- About MariaDB: https://mariadb.org/documentation/
- Creating an AWS Account: https://portal.aws.amazon.com/billing/signup#/start
- Installing AWS Version 2 CLI: https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2-windows.html
- Installing Terraform: https://www.terraform.io/downloads.html
- About Amazon VPC: https://docs.aws.amazon.com/vpc/latest/userguide/what-is-amazon-vpc.html
- About NAT Gateways in AWS: https://docs.aws.amazon.com/vpc/latest/userguide/vpc-nat-gateway.html
- Hosting WordPress in AWS EC2 instances: https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/hosting-wordpress.html
- Setting up MariaDB in AWS EC2 instances: https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/ec2-lamp-amazon-linux-2.html
The files used in this article can also be found in this repository.
You can find more of my work using AWS below:
- Working with AWS, Terraform and GitHub — Part I: https://medium.com/@akshayavb99/integration-of-aws-terraform-and-github-for-automated-deployment-infrastructure-da0a19ff4e86?source=friends_link&sk=4abceec1300554fdca0dba72090cf506
- Working with AWS, Terraform and GitHub — Part II: https://medium.com/@akshayavb99/working-with-aws-terraform-and-github-part-ii-c8c5bb5db1fe?source=friends_link&sk=263fa65899b998e7eb157ca178c121b0
- Hosting WordPress and MySQL Database using AWS: https://medium.com/@akshayavb99/working-with-aws-and-terraform-for-naas-an-introduction-16b84797d86e?source=friends_link&sk=ef16b7543f9493a76ffb7ed3e8b17edc