VPC with no Landing Zone ¶
What ¶
Do you want to try binbash Leverage but you are not willing to transform yet your already existent infra to the binbash Leverage Landing Zone (honoring the AWS Well Architected Framework)?
With this cookbook you will create a VPC with all the benefits binbash Leverage network layer provides.
If you want to use the Full binbash Leverage Landing Zone please visit the Try Leverage section
This will give you the full power of binbash Leverage and the AWS Well Architected Framework.
Why ¶
Maybe because you found binbash Leverage but you want to try it out first before you convert your base infra.
How ¶
Objective ¶
We will create a simple VPC (with all its resources) and an will add an EC2 instance to it so we can test it for real.
What you need: ¶
- an AWS account
- a user with programmatic access keys and the keys
- binbash Leverage
Common Process ¶
Ok, just install binbash Leverage and create the Leverage project. When creating credentials, do it for MANAGEMENT type. Basically:
mkdir project && cd project
leverage project init
## edit the yaml file
leverage project create
leverage credentials configure --type MANAGEMENT
You end up with this structure:
❯ tree -L 2 .
.
├── build.env
├── config
│ └── common.tfvars
├── management
│ ├── config
│ ├── global
│ └── us-east-1
├── Pipfile
├── Pipfile.lock
├── project.yaml
├── security
│ ├── config
│ └── us-east-1
└── shared
├── config
└── us-east-1
Create a dummy account dir.
Despite we won't create a real account (since there is no Landing Zone), we'll have to create a dir to hold all the layers we need.
mkdir -p apps-dummy/us-east-1/
Copy the config files:
cp -r shared/config apps-dummy/
In config/account.tfvars
change this:
## Environment Name
environment = "shared"
## Environment Name
environment = "apps-dummy"
In config/backend.tfvars
change this:
profile = "bm-shared-oaar"
profile = "bm-management"
VPC Process ¶
Copy the network layer:
cp -r shared/us-east-1/base-network apps-dummy/us-east-1/
Go into the layer:
cp -r shared/us-east-1/base-network apps-dummy/us-east-1/
cd apps-dummy/us-east-1/base-network
Since we are testing we won't use the S3 backend (we didn't create the bucket, but you can do it easily with the base-tf-backend
layer), so comment this line in config.tf
file:
#backend "s3" {
# key = "shared/network/terraform.tfstate"
#}
Initialize the layer:
leverage tf init --skip-validation
Note the skip-validation
flag. This is needed since we are using local tfstate.
Plan it:
leverage tf plan
If you are happy (or you are unhappy but you are ok with the plan), apply it:
leverage tf apply
You should end up with something like this:
Apply complete! Resources: 20 added, 0 changed, 0 destroyed.
Outputs:
availability_zones = [
"us-east-1a",
"us-east-1b",
]
nat_gateway_ids = []
private_route_table_ids = [
"rtb-065deXXXXXXX86b6d",
]
private_subnets = [
"subnet-0aXXXXXXXXXXd80a6",
"subnet-0bXXXXXXXXXX0ff67",
]
private_subnets_cidr = [
"172.18.0.0/21",
]
public_route_table_ids = [
"rtb-01XXXXXXXXXXXX887",
]
public_subnets = [
"subnet-0648XXXXXXXXX69",
"subnet-0297XXXXXXXXf10",
]
public_subnets_cidr = [
"172.18.8.0/21",
]
vpc_cidr_block = "172.18.0.0/20"
vpc_id = "vpc-0aXXXXXXXXXX06d8f"
vpc_name = "bm-apps-dummy-vpc"
EC2 Process ¶
Great, now we can go for the EC2!
Get the layer ¶
For this step we'll go for a layer that can be found in the binbash Leverage RefArch under this directory.
You can download a directory from a git repository using this Firefox addon or any method you want.
Note when you copy the layer (e.g. with gitzip), the file common-variables.tf
, which is a soft link, was probably copied as a regular file.
If this happens, delete it:
cd ec2-fleet-ansible\ --
rm common-variables.tf
Prepare the layer ¶
Again, since we are not running the whole binbash Leverage Landing Zone we need to comment out these lines in config.tf
:
#backend "s3" {
# key = "apps-devstg/ec2-fleet-ansible/terraform.tfstate"
#}
Also in this file, comment out these two resources:
data "terraform_remote_state" "security" {
data "terraform_remote_state" "vpc-shared" {
And change vpc
to be like this:
data "terraform_remote_state" "vpc" {
backend = "local"
config = {
path = "../base-network/terraform.tfstate"
}
}
In ec2_fleet.tf
update module version like this:
source = "github.com/binbashar/terraform-aws-ec2-instance.git?ref=v5.5.0"
Init the layer:
leverage tf init --skip-validation
Now, we need some common and specific vars that are not set.
So, create a variables.tf
file with this content:
variable "environment" {
type = string
description = "Environment Name"
}
variable "profile" {
type = string
description = "AWS Profile (required by the backend but also used for other resources)"
}
variable "region" {
type = string
description = "AWS Region"
}
##=============================#
## EC2 Attributes #
##=============================#
variable "aws_ami_os_id" {
type = string
description = "AWS AMI Operating System Identificator"
default = "ubuntu/images/hvm-ssd/ubuntu-jammy-22.04-amd64-server-*"
}
variable "aws_ami_os_owner" {
type = string
description = "AWS AMI Operating System Owner, eg: 099720109477 for Canonical "
default = "099720109477"
}
## security.tf file
##=============================#
## SSM Attributes #
##=============================#
variable "instance_profile" {
type = string
description = "Whether or not to create the EC2 profile, use null or 'true'"
default = "true"
}
variable "prefix" {
type = string
description = "EC2 profile prefix"
default = "fleet-ansible"
}
variable "name" {
type = string
description = "EC2 profile name"
default = "ssm-demo"
}
variable "enable_ssm_access" {
type = bool
description = "Whether or not to attach SSM policy to EC2 profile IAM role, use false or true"
default = true
}
In ec2_fleet.tf
file comment these lines:
# data.terraform_remote_state.vpc-shared.outputs.vpc_cidr_block
# key_name = data.terraform_remote_state.security.outputs.aws_key_pair_name
If you plan to access the instance from the Internet (EC2 in a public subnet)(e.g. to use Ansible), you change the first line to "0.0.0.0/0"
. (or better, a specific public IP)
If you want to add an SSH key (e.g. to use Ansible), you can generate a new SSH key, add a resource like this:
resource "aws_key_pair" "devops" {
key_name = "devops-key"
public_key = "ssh-ed25519 AAAAC3N9999999999999999999999999eF Binbash-AWS-instances"
}
ec2_fleet.tf
with this one:
key_name = aws_key_pair.devops.key_name
In the same file, change instance_type
as per your needs.
Also you can add this
* * *to the ec2_ansible_fleet
resource:
create_spot_instance = true
create_iam_instance_profile = true
iam_role_description = "IAM role for EC2 instance"
iam_role_policies = {
AmazonSSMManagedInstanceCore = "arn:aws:iam::aws:policy/AmazonSSMManagedInstanceCore"
}
In locals.tf
file check the variable multiple_instances
. There the EC2 instances are defined, by default there are four.
Remember to set the subnets in which the instances will be created.
Finally, apply the layer:
leverage tf apply
Check your public IP and try to SSH into your new instance!
Have fun!