Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TM-536, updating APEX WAF from Classic to new WAFv2 #9198

Open
wants to merge 8 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion terraform/environments/apex/cloudfront.tf
Original file line number Diff line number Diff line change
Expand Up @@ -250,7 +250,7 @@ resource "aws_cloudfront_distribution" "external" {
prefix = local.application_name
}

web_acl_id = aws_waf_web_acl.waf_acl.id
web_acl_id = aws_wafv2_web_acl.waf_acl.arn

# This is a required block in Terraform. Here we are having no geo restrictions.
restrictions {
Expand Down
145 changes: 93 additions & 52 deletions terraform/environments/apex/waf.tf
Original file line number Diff line number Diff line change
Expand Up @@ -13,78 +13,119 @@ locals {
ip_set_list = local.environment == "development" ? local.ip_set_dev : local.ip_set_prod
}

resource "aws_waf_ipset" "wafmanualallowset" {
name = "${upper(local.application_name)} Manual Allow Set"
resource "aws_wafv2_ip_set" "wafmanualallowset" {
name = "${upper(local.application_name)}-manual-allow-set"

# Ranges from https://github.com/ministryofjustice/laa-apex/blob/master/aws/application/application_stack.template
# removed redundant ip addresses such as RedCentric access and AWS Holborn offices Wifi

dynamic "ip_set_descriptors" {
for_each = local.ip_set_list
content {
type = "IPV4"
value = ip_set_descriptors.value
}
}

scope = "CLOUDFRONT"
provider = aws.us-east-1
ip_address_version = "IPV4"
description = "Manual Allow Set for ${local.application_name} WAF"
addresses = local.ip_set_list
}

resource "aws_waf_ipset" "wafmanualblockset" {
name = "${upper(local.application_name)} Manual Block Set"
resource "aws_wafv2_ip_set" "wafmanualblockset" {
name = "${upper(local.application_name)}-manual-block-set"
scope = "CLOUDFRONT"
provider = aws.us-east-1
description = "Manual Block Set for ${local.application_name} WAF"
ip_address_version = "IPV4"
addresses = []
}

resource "aws_waf_rule" "wafmanualallowrule" {
depends_on = [aws_waf_ipset.wafmanualallowset]
name = "${upper(local.application_name)} Manual Allow Rule"
metric_name = "${upper(local.application_name)}ManualAllowRule"
resource "aws_wafv2_rule_group" "manual-rules" {
name = "${upper(local.application_name)}-manual-rules"
provider = aws.us-east-1
scope = "CLOUDFRONT" # Use "CLOUDFRONT" for CloudFront
capacity = 10 # Adjust based on complexity
description = "Manual Allow/Block Rules for ${local.application_name}"

rule {
name = "AllowIPs"
priority = 1

predicates {
data_id = aws_waf_ipset.wafmanualallowset.id
negated = false
type = "IPMatch"
statement {
ip_set_reference_statement {
arn = aws_wafv2_ip_set.wafmanualallowset.arn
}
}

action {
allow {}
}

visibility_config {
sampled_requests_enabled = true
cloudwatch_metrics_enabled = true
metric_name = "AllowIPs"
}
}
}

resource "aws_waf_rule" "wafmanualblockrule" {
depends_on = [aws_waf_ipset.wafmanualblockset]
name = "${upper(local.application_name)} Manual Block Rule"
metric_name = "${upper(local.application_name)}ManualBlockRule"
rule {
name = "BlockIPs"
priority = 2

statement {
ip_set_reference_statement {
arn = aws_wafv2_ip_set.wafmanualblockset.arn
}
}

predicates {
data_id = aws_waf_ipset.wafmanualblockset.id
negated = false
type = "IPMatch"
action {
block {}
}

visibility_config {
sampled_requests_enabled = true
cloudwatch_metrics_enabled = true
metric_name = "BlockIPs"
}
}

visibility_config {
sampled_requests_enabled = true
cloudwatch_metrics_enabled = true
metric_name = "ManualRulesGroup"
}
}

resource "aws_waf_web_acl" "waf_acl" {
depends_on = [
aws_waf_rule.wafmanualallowrule,
aws_waf_rule.wafmanualblockrule,
]
name = "${upper(local.application_name)} Whitelisting Requesters"
metric_name = "${upper(local.application_name)}WhitelistingRequesters"
# scope = "CLOUDFRONT"
# provider = aws.us-east-1
resource "aws_wafv2_web_acl" "waf_acl" {
name = "${upper(local.application_name)}-Whitelisting-Requesters"
provider = aws.us-east-1
scope = "CLOUDFRONT" # Use "CLOUDFRONT" for CloudFront
description = "Web ACL for ${local.application_name}"

default_action {
type = "BLOCK"
block {}
}

rules {
action {
type = "ALLOW"
}
rule {
name = "ManualAllowBlockRules"
priority = 1
rule_id = aws_waf_rule.wafmanualallowrule.id
type = "REGULAR"
}

rules {
action {
type = "BLOCK"
statement {
rule_group_reference_statement {
arn = aws_wafv2_rule_group.manual-rules.arn
}
}
priority = 2
rule_id = aws_waf_rule.wafmanualblockrule.id
type = "REGULAR"

override_action {
none {}
}

visibility_config {
sampled_requests_enabled = true
cloudwatch_metrics_enabled = true
metric_name = "ManualAllowBlockRules"
}
}

visibility_config {
sampled_requests_enabled = true
cloudwatch_metrics_enabled = true
metric_name = "${upper(local.application_name)}-Whitelisting-Requesters"
}
}

Expand Down
Loading