├── versions.tf ├── examples ├── ec2 │ ├── versions.tf │ ├── variables.tf │ └── main.tf └── simple │ ├── versions.tf │ ├── variables.tf │ └── main.tf ├── .gitignore ├── .pre-commit-config.yaml ├── public.tf ├── private.tf ├── .chglog ├── config.yml └── CHANGELOG.tpl.md ├── CHANGELOG.md ├── .github └── workflows │ └── main.yml ├── main.tf ├── LICENSE ├── nat.tf ├── variables.tf ├── flow_log.tf ├── outputs.tf └── README.md /versions.tf: -------------------------------------------------------------------------------- 1 | 2 | terraform { 3 | required_version = ">= 0.12" 4 | } 5 | -------------------------------------------------------------------------------- /examples/ec2/versions.tf: -------------------------------------------------------------------------------- 1 | 2 | terraform { 3 | required_version = ">= 0.12" 4 | } 5 | -------------------------------------------------------------------------------- /examples/simple/versions.tf: -------------------------------------------------------------------------------- 1 | 2 | terraform { 3 | required_version = ">= 0.12" 4 | } 5 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Compiled files 2 | *.tfstate 3 | *.tfstate.backup 4 | 5 | # Module directory 6 | .terraform/ 7 | 8 | *.tfvars -------------------------------------------------------------------------------- /.pre-commit-config.yaml: -------------------------------------------------------------------------------- 1 | - repo: git://github.com/antonbabenko/pre-commit-terraform 2 | rev: v1.30.0 3 | hooks: 4 | - id: terraform_fmt 5 | - id: terraform_docs 6 | -------------------------------------------------------------------------------- /examples/simple/variables.tf: -------------------------------------------------------------------------------- 1 | variable "access_key" { 2 | } 3 | 4 | variable "secret_key" { 5 | } 6 | 7 | variable "region" { 8 | description = "The AWS region in which global resources are set up." 9 | default = "us-east-1" 10 | } 11 | -------------------------------------------------------------------------------- /examples/ec2/variables.tf: -------------------------------------------------------------------------------- 1 | variable "access_key" { 2 | } 3 | 4 | variable "secret_key" { 5 | } 6 | 7 | variable "region" { 8 | description = "The AWS region in which global resources are set up." 9 | default = "us-east-1" 10 | } 11 | 12 | variable "management_ip" { 13 | description = "The IP address from which an administrator connects to instances via SSH." 14 | } 15 | 16 | variable "key_name" { 17 | description = "The key name to use for EC2 instances." 18 | } 19 | 20 | -------------------------------------------------------------------------------- /public.tf: -------------------------------------------------------------------------------- 1 | #--------------------------------------------------------------------------------------------------- 2 | # Configurations for public subnets 3 | #--------------------------------------------------------------------------------------------------- 4 | resource "aws_internet_gateway" "gw" { 5 | vpc_id = aws_vpc.this.id 6 | tags = var.tags 7 | } 8 | 9 | resource "aws_route_table" "public" { 10 | vpc_id = aws_vpc.this.id 11 | 12 | route { 13 | cidr_block = "0.0.0.0/0" 14 | gateway_id = aws_internet_gateway.gw.id 15 | } 16 | 17 | tags = var.tags 18 | } 19 | 20 | -------------------------------------------------------------------------------- /private.tf: -------------------------------------------------------------------------------- 1 | #--------------------------------------------------------------------------------------------------- 2 | # Configurations for private subnets 3 | #--------------------------------------------------------------------------------------------------- 4 | 5 | resource "aws_route_table" "private" { 6 | vpc_id = aws_vpc.this.id 7 | 8 | route { 9 | cidr_block = "0.0.0.0/0" 10 | nat_gateway_id = aws_nat_gateway.gw[0].id 11 | } 12 | 13 | tags = var.tags 14 | } 15 | 16 | resource "aws_main_route_table_association" "default_to_private" { 17 | vpc_id = aws_vpc.this.id 18 | route_table_id = aws_route_table.private.id 19 | } 20 | 21 | -------------------------------------------------------------------------------- /.chglog/config.yml: -------------------------------------------------------------------------------- 1 | style: github 2 | template: CHANGELOG.tpl.md 3 | info: 4 | title: CHANGELOG 5 | repository_url: https://github.com/nozaq/terraform-aws-secure-baseline 6 | options: 7 | commits: 8 | filters: 9 | Type: 10 | - feat 11 | - fix 12 | - perf 13 | - refactor 14 | commit_groups: 15 | # title_maps: 16 | # feat: Features 17 | # fix: Bug Fixes 18 | # perf: Performance Improvements 19 | # refactor: Code Refactoring 20 | header: 21 | pattern: "^(\\w*)\\:\\s(.*)$" 22 | pattern_maps: 23 | - Type 24 | - Subject 25 | notes: 26 | keywords: 27 | - BREAKING CHANGE 28 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | 2 | ## [Unreleased] 3 | 4 | 5 | 6 | ## [0.1.1] - 2019-10-13 7 | ### Fix 8 | - the AWS region is hard-coded in the key policy 9 | 10 | 11 | 12 | ## [0.1.0] - 2019-10-13 13 | ### Fix 14 | - log_group_name deprecation warning 15 | 16 | 17 | 18 | ## [0.0.2] - 2019-10-13 19 | ### Feat 20 | - upgrade to Terraform 0.12 syntax 21 | 22 | 23 | 24 | ## 0.0.1 - 2018-05-04 25 | 26 | [Unreleased]: https://github.com/nozaq/terraform-aws-secure-baseline/compare/0.1.1...HEAD 27 | [0.1.1]: https://github.com/nozaq/terraform-aws-secure-baseline/compare/0.1.0...0.1.1 28 | [0.1.0]: https://github.com/nozaq/terraform-aws-secure-baseline/compare/0.0.2...0.1.0 29 | [0.0.2]: https://github.com/nozaq/terraform-aws-secure-baseline/compare/0.0.1...0.0.2 30 | -------------------------------------------------------------------------------- /.github/workflows/main.yml: -------------------------------------------------------------------------------- 1 | name: Terraform 2 | on: 3 | push: 4 | branches: 5 | - main 6 | pull_request: 7 | env: 8 | TF_ACTIONS_VERSION: latest 9 | jobs: 10 | check-format: 11 | name: Check format 12 | runs-on: ubuntu-latest 13 | steps: 14 | - uses: hashicorp/setup-terraform@v1 15 | - name: Checkout 16 | uses: actions/checkout@v2 17 | - name: "Terraform Format" 18 | run: terraform fmt -check -recursive 19 | 20 | validate-examples: 21 | name: Validate examples 22 | runs-on: ubuntu-latest 23 | defaults: 24 | run: 25 | shell: bash 26 | working-directory: examples 27 | steps: 28 | - uses: hashicorp/setup-terraform@v1 29 | - name: Checkout 30 | uses: actions/checkout@v2 31 | - name: Check examples 32 | env: 33 | EXAMPLES: simple ec2 34 | run: | 35 | for EXAMPLE in ${EXAMPLES} 36 | do 37 | echo "Validating $EXAMPLE"... 38 | cd $EXAMPLE && terraform init && terraform validate && cd - 39 | done 40 | -------------------------------------------------------------------------------- /main.tf: -------------------------------------------------------------------------------- 1 | #--------------------------------------------------------------------------------------------------- 2 | # VPC 3 | #--------------------------------------------------------------------------------------------------- 4 | resource "aws_vpc" "this" { 5 | cidr_block = var.cidr_block 6 | instance_tenancy = var.instance_tenancy 7 | enable_dns_support = var.enable_dns_support 8 | enable_dns_hostnames = var.enable_dns_hostnames 9 | assign_generated_ipv6_cidr_block = var.assign_generated_ipv6_cidr_block 10 | tags = var.tags 11 | } 12 | 13 | resource "aws_default_security_group" "default" { 14 | vpc_id = aws_vpc.this.id 15 | tags = var.tags 16 | } 17 | 18 | resource "aws_default_network_acl" "default" { 19 | default_network_acl_id = aws_vpc.this.default_network_acl_id 20 | tags = var.tags 21 | } 22 | 23 | resource "aws_default_route_table" "default" { 24 | default_route_table_id = aws_vpc.this.default_route_table_id 25 | tags = var.tags 26 | } 27 | 28 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 Takashi Nozawa 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /.chglog/CHANGELOG.tpl.md: -------------------------------------------------------------------------------- 1 | {{ if .Versions -}} 2 | 3 | ## [Unreleased] 4 | 5 | {{ if .Unreleased.CommitGroups -}} 6 | {{ range .Unreleased.CommitGroups -}} 7 | ### {{ .Title }} 8 | {{ range .Commits -}} 9 | - {{ if .Scope }}**{{ .Scope }}:** {{ end }}{{ .Subject }} 10 | {{ end }} 11 | {{ end -}} 12 | {{ end -}} 13 | {{ end -}} 14 | 15 | {{ range .Versions }} 16 | 17 | ## {{ if .Tag.Previous }}[{{ .Tag.Name }}]{{ else }}{{ .Tag.Name }}{{ end }} - {{ datetime "2006-01-02" .Tag.Date }} 18 | {{ range .CommitGroups -}} 19 | ### {{ .Title }} 20 | {{ range .Commits -}} 21 | - {{ if .Scope }}**{{ .Scope }}:** {{ end }}{{ .Subject }} 22 | {{ end }} 23 | {{ end -}} 24 | 25 | {{- if .NoteGroups -}} 26 | {{ range .NoteGroups -}} 27 | ### {{ .Title }} 28 | {{ range .Notes }} 29 | {{ .Body }} 30 | {{ end }} 31 | {{ end -}} 32 | {{ end -}} 33 | {{ end -}} 34 | 35 | {{- if .Versions }} 36 | [Unreleased]: {{ .Info.RepositoryURL }}/compare/{{ $latest := index .Versions 0 }}{{ $latest.Tag.Name }}...HEAD 37 | {{ range .Versions -}} 38 | {{ if .Tag.Previous -}} 39 | [{{ .Tag.Name }}]: {{ $.Info.RepositoryURL }}/compare/{{ .Tag.Previous.Name }}...{{ .Tag.Name }} 40 | {{ end -}} 41 | {{ end -}} 42 | {{ end -}} 43 | -------------------------------------------------------------------------------- /examples/simple/main.tf: -------------------------------------------------------------------------------- 1 | #--------------------------------------------------------------------------------------------------- 2 | # Example Configuration w/ public & private subnets 3 | #--------------------------------------------------------------------------------------------------- 4 | 5 | locals { 6 | vpc_cidr = "10.0.0.0/16" 7 | nat_cidr = "10.0.254.0/24" 8 | dmz_cidr = "10.0.0.0/24" 9 | private_cidr = "10.0.1.0/24" 10 | } 11 | 12 | #--------------------------------------------------------------------------------------------------- 13 | # VPC 14 | #--------------------------------------------------------------------------------------------------- 15 | provider "aws" { 16 | access_key = var.access_key 17 | secret_key = var.secret_key 18 | region = var.region 19 | } 20 | 21 | data "aws_caller_identity" "current" { 22 | } 23 | 24 | module "simple_vpc" { 25 | source = "../../" 26 | 27 | aws_account_id = data.aws_caller_identity.current.account_id 28 | cidr_block = local.vpc_cidr 29 | availability_zones = ["us-east-1a"] 30 | nat_subnet_cidr_blocks = [local.nat_cidr] 31 | flow_logs_iam_role_name = "FlowLogsPublisher" 32 | flow_logs_group_name = "SimpleVPCFlowLogs" 33 | 34 | tags = { 35 | Environment = "SimpleVPC" 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /nat.tf: -------------------------------------------------------------------------------- 1 | #--------------------------------------------------------------------------------------------------- 2 | # NAT Gateway 3 | #--------------------------------------------------------------------------------------------------- 4 | resource "aws_subnet" "nat" { 5 | count = length(var.availability_zones) 6 | vpc_id = aws_vpc.this.id 7 | cidr_block = var.nat_subnet_cidr_blocks[count.index] 8 | availability_zone = var.availability_zones[count.index] 9 | tags = var.tags 10 | } 11 | 12 | resource "aws_route_table_association" "dmz" { 13 | count = length(var.availability_zones) 14 | subnet_id = aws_subnet.nat[count.index].id 15 | route_table_id = aws_route_table.public.id 16 | } 17 | 18 | resource "aws_network_acl" "nat" { 19 | vpc_id = aws_vpc.this.id 20 | subnet_ids = [aws_subnet.nat[0].id] 21 | 22 | # allow all traffic from instances inside the VPC. 23 | ingress { 24 | protocol = "all" 25 | rule_no = 100 26 | action = "allow" 27 | cidr_block = var.cidr_block 28 | from_port = 0 29 | to_port = 0 30 | } 31 | 32 | # allow all returning traffic from the internet. 33 | ingress { 34 | protocol = "tcp" 35 | rule_no = 110 36 | action = "allow" 37 | cidr_block = "0.0.0.0/0" 38 | from_port = 1024 39 | to_port = 65535 40 | } 41 | 42 | # allow all traffic to the internet. 43 | egress { 44 | protocol = "all" 45 | rule_no = 100 46 | action = "allow" 47 | cidr_block = "0.0.0.0/0" 48 | from_port = 0 49 | to_port = 0 50 | } 51 | 52 | tags = var.tags 53 | } 54 | 55 | resource "aws_eip" "nat" { 56 | count = length(var.availability_zones) 57 | vpc = true 58 | tags = var.tags 59 | } 60 | 61 | resource "aws_nat_gateway" "gw" { 62 | count = length(var.availability_zones) 63 | allocation_id = aws_eip.nat[count.index].id 64 | subnet_id = aws_subnet.nat[count.index].id 65 | tags = var.tags 66 | } 67 | 68 | -------------------------------------------------------------------------------- /variables.tf: -------------------------------------------------------------------------------- 1 | #--------------------------------------------------------------------------------------------------- 2 | # General 3 | #--------------------------------------------------------------------------------------------------- 4 | 5 | variable "aws_account_id" { 6 | description = "The AWS Account ID number of the account." 7 | } 8 | 9 | variable "tags" { 10 | description = "Tags to be attached to all resources created with this module." 11 | default = {} 12 | } 13 | 14 | #--------------------------------------------------------------------------------------------------- 15 | # VPC 16 | #--------------------------------------------------------------------------------------------------- 17 | 18 | variable "cidr_block" { 19 | description = "The CIDR block for the VPC." 20 | } 21 | 22 | variable "availability_zones" { 23 | description = "The availability zones to support with this VPC." 24 | default = [] 25 | } 26 | 27 | variable "nat_subnet_cidr_blocks" { 28 | description = "The CIDR blocks for the NAT subnets." 29 | default = [] 30 | } 31 | 32 | variable "instance_tenancy" { 33 | description = "A tenancy option for instances launched into the VPC" 34 | default = "default" 35 | } 36 | 37 | variable "enable_dns_support" { 38 | description = "A boolean flag to enable/disable DNS support in the VPC." 39 | default = true 40 | } 41 | 42 | variable "enable_dns_hostnames" { 43 | description = "A boolean flag to enable/disable DNS hostnames in the VPC." 44 | default = false 45 | } 46 | 47 | variable "assign_generated_ipv6_cidr_block" { 48 | description = "Requests an Amazon-provided IPv6 CIDR block with a /56 prefix length for the VPC. You cannot specify the range of IP addresses, or the size of the CIDR block." 49 | default = false 50 | } 51 | 52 | #--------------------------------------------------------------------------------------------------- 53 | # VPC Flow Logs 54 | #--------------------------------------------------------------------------------------------------- 55 | 56 | variable "flow_logs_group_name" { 57 | description = "The name of the CloudWatch Logs group for VPC Flow Logs." 58 | } 59 | 60 | variable "flow_logs_iam_role_name" { 61 | description = "The name of the IAM role to publish VPC Flow Logs." 62 | } 63 | 64 | variable "flow_logs_retention_in_days" { 65 | description = "Specifies the number of days you want to retain VPC Flow Logs events." 66 | default = "0" 67 | } 68 | 69 | variable "flow_logs_traffic_type" { 70 | description = "The type of traffic to capture. Valid values: ACCEPT,REJECT, ALL" 71 | default = "ALL" 72 | } 73 | 74 | variable "flow_logs_key_deletion_window_in_days" { 75 | description = "Duration in days after which the key is deleted after destruction of the resource, must be between 7 and 30 days. Defaults to 30 days." 76 | default = "30" 77 | } 78 | 79 | -------------------------------------------------------------------------------- /flow_log.tf: -------------------------------------------------------------------------------- 1 | data "aws_region" "current" {} 2 | 3 | #--------------------------------------------------------------------------------------------------- 4 | # VPC Flow Logs 5 | #--------------------------------------------------------------------------------------------------- 6 | 7 | resource "aws_kms_key" "flow_logs" { 8 | description = "A KMS Key for encrypting VPC Flow Logs." 9 | enable_key_rotation = true 10 | deletion_window_in_days = var.flow_logs_key_deletion_window_in_days 11 | 12 | policy = < 41 | ## Inputs 42 | 43 | | Name | Description | Type | Default | Required | 44 | |------|-------------|:----:|:-----:|:-----:| 45 | | assign\_generated\_ipv6\_cidr\_block | Requests an Amazon-provided IPv6 CIDR block with a /56 prefix length for the VPC. You cannot specify the range of IP addresses, or the size of the CIDR block. | string | `"false"` | no | 46 | | availability\_zones | The availability zones to support with this VPC. | list | `[]` | no | 47 | | aws\_account\_id | The AWS Account ID number of the account. | string | n/a | yes | 48 | | cidr\_block | The CIDR block for the VPC. | string | n/a | yes | 49 | | enable\_dns\_hostnames | A boolean flag to enable/disable DNS hostnames in the VPC. | string | `"false"` | no | 50 | | enable\_dns\_support | A boolean flag to enable/disable DNS support in the VPC. | string | `"true"` | no | 51 | | flow\_logs\_group\_name | The name of the CloudWatch Logs group for VPC Flow Logs. | string | n/a | yes | 52 | | flow\_logs\_iam\_role\_name | The name of the IAM role to publish VPC Flow Logs. | string | n/a | yes | 53 | | flow\_logs\_key\_deletion\_window\_in\_days | Duration in days after which the key is deleted after destruction of the resource, must be between 7 and 30 days. Defaults to 30 days. | string | `"30"` | no | 54 | | flow\_logs\_retention\_in\_days | Specifies the number of days you want to retain VPC Flow Logs events. | string | `"0"` | no | 55 | | flow\_logs\_traffic\_type | The type of traffic to capture. Valid values: ACCEPT,REJECT, ALL | string | `"ALL"` | no | 56 | | instance\_tenancy | A tenancy option for instances launched into the VPC | string | `"default"` | no | 57 | | nat\_subnet\_cidr\_blocks | The CIDR blocks for the NAT subnets. | list | `[]` | no | 58 | | tags | Tags to be attached to all resources created with this module. | map | `{}` | no | 59 | 60 | ## Outputs 61 | 62 | | Name | Description | 63 | |------|-------------| 64 | | default\_network\_acl\_id | The ID of the default network ACL | 65 | | default\_route\_table\_id | The ID of the default route table | 66 | | default\_security\_group\_id | The ID of the security group created by default on VPC creation | 67 | | flow\_logs\_group\_arn | The ARN of the CloudWatch log group to which VPC Flow Logs will publish to. | 68 | | internet\_gateway\_id | The ID of the internet gateawy | 69 | | nat\_gateway\_ids | The ID of the NAT Gateawy | 70 | | nat\_gateway\_private\_ips | The private IP address of the NAT Gateway | 71 | | nat\_gateway\_public\_ips | The public IP address of the NAT Gateway | 72 | | private\_route\_table\_id | The ID of the route table for private subnets | 73 | | public\_route\_table\_id | The ID of the route table for public subnets | 74 | | vpc\_cidr\_block | The CIDR block of the VPC | 75 | | vpc\_enable\_dns\_hostnames | Whether or not the VPC has DNS hostname support | 76 | | vpc\_enable\_dns\_support | Whether or not the VPC has DNS support | 77 | | vpc\_id | The ID of the VPC | 78 | | vpc\_instance\_tenancy | Tenancy of instances spin up within VPC | 79 | | vpc\_main\_route\_table\_id | The ID of the main route table associated with this VPC | 80 | 81 | 82 | 83 | [CIS Amazon Web Services Foundations]: https://d0.awsstatic.com/whitepapers/compliance/AWS_CIS_Foundations_Benchmark.pdf 84 | [CIS Amazon Web Services Three-tier Web Architecture Benchmark]: https://d1.awsstatic.com/whitepapers/compliance/CIS_Amazon_Web_Services_Three-tier_Web_Architecture_Benchmark.pdf -------------------------------------------------------------------------------- /examples/ec2/main.tf: -------------------------------------------------------------------------------- 1 | #--------------------------------------------------------------------------------------------------- 2 | # Example Configuration w/ public & private subnets 3 | #--------------------------------------------------------------------------------------------------- 4 | 5 | locals { 6 | vpc_cidr = "10.0.0.0/16" 7 | nat_cidr = "10.0.254.0/24" 8 | dmz_cidr = "10.0.0.0/24" 9 | private_cidr = "10.0.1.0/24" 10 | } 11 | 12 | #--------------------------------------------------------------------------------------------------- 13 | # VPC 14 | #--------------------------------------------------------------------------------------------------- 15 | provider "aws" { 16 | access_key = var.access_key 17 | secret_key = var.secret_key 18 | region = var.region 19 | } 20 | 21 | data "aws_caller_identity" "current" { 22 | } 23 | 24 | module "simple_vpc" { 25 | source = "../../" 26 | 27 | aws_account_id = data.aws_caller_identity.current.account_id 28 | cidr_block = local.vpc_cidr 29 | availability_zones = ["us-east-1a"] 30 | nat_subnet_cidr_blocks = [local.nat_cidr] 31 | flow_logs_iam_role_name = "FlowLogsPublisher" 32 | flow_logs_group_name = "SimpleVPCFlowLogs" 33 | 34 | tags = { 35 | Environment = "SimpleVPC" 36 | } 37 | } 38 | 39 | data "aws_ami" "amazon_linux" { 40 | most_recent = true 41 | owners = ["amazon"] 42 | 43 | filter { 44 | name = "architecture" 45 | values = ["x86_64"] 46 | } 47 | 48 | filter { 49 | name = "root-device-type" 50 | values = ["ebs"] 51 | } 52 | 53 | filter { 54 | name = "name" 55 | values = ["amzn-ami-hvm-*"] 56 | } 57 | 58 | filter { 59 | name = "virtualization-type" 60 | values = ["hvm"] 61 | } 62 | 63 | filter { 64 | name = "block-device-mapping.volume-type" 65 | values = ["gp2"] 66 | } 67 | } 68 | 69 | #--------------------------------------------------------------------------------------------------- 70 | # Public Subnet 71 | #--------------------------------------------------------------------------------------------------- 72 | 73 | resource "aws_subnet" "dmz" { 74 | vpc_id = module.simple_vpc.vpc_id 75 | cidr_block = local.dmz_cidr 76 | } 77 | 78 | resource "aws_route_table_association" "dmz" { 79 | subnet_id = aws_subnet.dmz.id 80 | route_table_id = module.simple_vpc.public_route_table_id 81 | } 82 | 83 | resource "aws_network_acl" "dmz" { 84 | vpc_id = module.simple_vpc.vpc_id 85 | subnet_ids = [aws_subnet.dmz.id] 86 | 87 | # allow all traffic from instances inside the VPC. 88 | ingress { 89 | protocol = "all" 90 | rule_no = 100 91 | action = "allow" 92 | cidr_block = var.management_ip 93 | from_port = 0 94 | to_port = 0 95 | } 96 | 97 | # allow all returning traffic from the internet. 98 | ingress { 99 | protocol = "tcp" 100 | rule_no = 110 101 | action = "allow" 102 | cidr_block = "0.0.0.0/0" 103 | from_port = 1024 104 | to_port = 65535 105 | } 106 | 107 | # allow all traffic to the internet. 108 | egress { 109 | protocol = "all" 110 | rule_no = 100 111 | action = "allow" 112 | cidr_block = "0.0.0.0/0" 113 | from_port = 0 114 | to_port = 0 115 | } 116 | } 117 | 118 | resource "aws_security_group" "bastion" { 119 | name = "BastionSG" 120 | description = "Allow all inbound traffic" 121 | vpc_id = module.simple_vpc.vpc_id 122 | 123 | ingress { 124 | from_port = 22 125 | to_port = 22 126 | protocol = "tcp" 127 | cidr_blocks = [var.management_ip] 128 | } 129 | 130 | egress { 131 | from_port = 0 132 | to_port = 0 133 | protocol = "-1" 134 | cidr_blocks = ["0.0.0.0/0"] 135 | } 136 | } 137 | 138 | resource "aws_instance" "bastion" { 139 | ami = data.aws_ami.amazon_linux.id 140 | instance_type = "t2.nano" 141 | subnet_id = aws_subnet.dmz.id 142 | vpc_security_group_ids = [aws_security_group.bastion.id] 143 | key_name = var.key_name 144 | associate_public_ip_address = true 145 | } 146 | 147 | #--------------------------------------------------------------------------------------------------- 148 | # Private Subnet 149 | #--------------------------------------------------------------------------------------------------- 150 | 151 | resource "aws_subnet" "private" { 152 | vpc_id = module.simple_vpc.vpc_id 153 | cidr_block = local.private_cidr 154 | } 155 | 156 | resource "aws_network_acl" "priavte" { 157 | vpc_id = module.simple_vpc.vpc_id 158 | subnet_ids = [aws_subnet.private.id] 159 | 160 | # allow all traffic from instances inside the VPC. 161 | ingress { 162 | protocol = "all" 163 | rule_no = 100 164 | action = "allow" 165 | cidr_block = local.dmz_cidr 166 | from_port = 0 167 | to_port = 0 168 | } 169 | 170 | # allow all returning traffic from the internet. 171 | ingress { 172 | protocol = "tcp" 173 | rule_no = 110 174 | action = "allow" 175 | cidr_block = "0.0.0.0/0" 176 | from_port = 1024 177 | to_port = 65535 178 | } 179 | 180 | # allow all traffic to the internet. 181 | egress { 182 | protocol = "all" 183 | rule_no = 100 184 | action = "allow" 185 | cidr_block = "0.0.0.0/0" 186 | from_port = 0 187 | to_port = 0 188 | } 189 | } 190 | 191 | resource "aws_security_group" "private" { 192 | name = "PrivateSG" 193 | description = "Allow all inbound traffic" 194 | vpc_id = module.simple_vpc.vpc_id 195 | 196 | ingress { 197 | from_port = 22 198 | to_port = 22 199 | protocol = "tcp" 200 | # TF-UPGRADE-TODO: In Terraform v0.10 and earlier, it was sometimes necessary to 201 | # force an interpolation expression to be interpreted as a list by wrapping it 202 | # in an extra set of list brackets. That form was supported for compatibilty in 203 | # v0.11, but is no longer supported in Terraform v0.12. 204 | # 205 | # If the expression in the following list itself returns a list, remove the 206 | # brackets to avoid interpretation as a list of lists. If the expression 207 | # returns a single list item then leave it as-is and remove this TODO comment. 208 | cidr_blocks = [local.dmz_cidr] 209 | } 210 | 211 | egress { 212 | from_port = 0 213 | to_port = 0 214 | protocol = "-1" 215 | cidr_blocks = ["0.0.0.0/0"] 216 | } 217 | } 218 | 219 | resource "aws_instance" "private" { 220 | ami = data.aws_ami.amazon_linux.id 221 | instance_type = "t2.nano" 222 | subnet_id = aws_subnet.private.id 223 | vpc_security_group_ids = [aws_security_group.private.id] 224 | key_name = var.key_name 225 | associate_public_ip_address = false 226 | } 227 | 228 | --------------------------------------------------------------------------------