From 293a2c232ec7e68ec077c5bfbf6aea721a75442d Mon Sep 17 00:00:00 2001 From: eddiek Date: Thu, 28 Nov 2024 10:00:09 +0000 Subject: [PATCH 1/2] Azure TF templates | Aligned route tables --- terraform/azure/modules/vnet/main.tf | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/terraform/azure/modules/vnet/main.tf b/terraform/azure/modules/vnet/main.tf index 2c67fc4f..17127b07 100755 --- a/terraform/azure/modules/vnet/main.tf +++ b/terraform/azure/modules/vnet/main.tf @@ -36,6 +36,7 @@ locals { // locals for 'next_hop_type' allowed values "VirtualAppliance", "None" ] + address_prefix_length = length(var.subnet_prefixes[0]) } resource "azurerm_route_table" "frontend" { @@ -51,7 +52,8 @@ resource "azurerm_route_table" "frontend" { route { name = "To-Internal" address_prefix = var.address_space - next_hop_type = local.next_hop_type_allowed_values[4] + next_hop_type = local.next_hop_type_allowed_values[3] + next_hop_in_ip_address = substr(replace(azurerm_subnet.subnet[0].address_prefixes[0], "0/", "4/"), 0, local.address_prefix_length - 3) } } @@ -69,7 +71,8 @@ resource "azurerm_route_table" "backend" { route { name = "To-Internet" address_prefix = "0.0.0.0/0" - next_hop_type = local.next_hop_type_allowed_values[4] + next_hop_type = local.next_hop_type_allowed_values[3] + next_hop_in_ip_address = substr(replace(azurerm_subnet.subnet[1].address_prefixes[0], "0/", "4/"), 0, local.address_prefix_length - 3) } } From 70545c44b4e8ca45c315eb83b0b6d664fcc8e2bb Mon Sep 17 00:00:00 2001 From: eddiek Date: Tue, 3 Dec 2024 11:19:55 +0000 Subject: [PATCH 2/2] Almogar dep onlygithub --- .gitignore | 5 +- aws/templates/cluster/README.md | 16 +- aws/templates/geo-cluster/README.md | 16 +- aws/templates/gwlb-asg/README.md | 15 + aws/templates/management/README.md | 15 +- aws/templates/single-gw/README.md | 15 + aws/templates/standalone/README.md | 15 + aws/templates/tgw-asg/README.md | 14 + aws/templates/tgw-cross-az-cluster/README.md | 14 +- aws/templates/tgw-ha/README.md | 15 +- .../{ => R77.30}/gateway-r7730/README.md | 0 .../gateway-2-nic-existing-vpc.json | 0 .../{ => R77.30}/gateways-r7730/README.md | 0 .../gateways-r7730/inter-az-cluster.json | 0 .../{ => R77.30}/instance-r7730/README.md | 0 .../{ => R77.30}/instance-r7730/gwinvpc.json | 0 .../{ => R77.30}/management-r7730/README.md | 0 .../management-r7730/r7730-management.json | 0 .../{ => R80.30}/asg-r8030/README.md | 0 .../{ => R80.30}/asg-r8030/autoscale.json | 0 .../{ => R80.30}/cluster-r8030/README.md | 0 .../cluster-r8030/cluster-into-vpc.json | 0 .../{ => R80.30}/cluster-r8030/cluster.json | 0 .../{ => R80.30}/management-r8030/README.md | 0 .../management-r8030/management.json | 0 .../{ => R80.30}/mds-r8030/README.md | 0 .../templates/{ => R80.30}/mds-r8030/mds.json | 0 .../{ => R80.30}/single-gw-r8030/README.md | 0 .../single-gw-r8030/gateway-into-vpc.json | 0 .../{ => R80.30}/single-gw-r8030/gateway.json | 0 .../{ => R80.30}/tgw-asg-r8030/README.md | 0 .../checkpoint-tgw-asg-master.yaml | 0 .../tgw-asg-r8030/checkpoint-tgw-asg.yaml | 0 .../{ => R80.30}/transit-vpc-r8030/README.md | 0 .../checkpoint-transit-master.yaml | 0 .../transit-vpc-r8030/checkpoint-transit.yaml | 0 .../transit-vpc-r8030/transit-master.yaml | 0 .../transit-vpc-r8030/transit.yaml | 0 .../templates/R80.40/autoscale/autoscale.yaml | 612 ++++++++ .../R80.40/autoscale/custom-autoscale.yaml | 226 +++ .../R80.40/autoscale/tgw-asg-master.yaml | 684 +++++++++ .../templates/R80.40/autoscale/tgw-asg.yaml | 676 +++++++++ .../R80.40/cluster/cluster-master.yaml | 512 +++++++ .../aws/templates/R80.40/cluster/cluster.yaml | 762 ++++++++++ .../R80.40/cluster/geo-cluster-master.yaml | 523 +++++++ .../templates/R80.40/cluster/geo-cluster.yaml | 734 +++++++++ .../R80.40/cluster/tgw-ha-master.yaml | 531 +++++++ .../aws/templates/R80.40/cluster/tgw-ha.yaml | 527 +++++++ .../R80.40/gateway/gateway-master.yaml | 495 +++++++ .../aws/templates/R80.40/gateway/gateway.yaml | 601 ++++++++ .../R80.40/gateway/standalone-master.yaml | 443 ++++++ .../templates/R80.40/gateway/standalone.yaml | 538 +++++++ .../aws/templates/R80.40/gwlb/amis-gwlb.yaml | 123 ++ .../templates/R80.40/gwlb/autoscale-gwlb.yaml | 657 ++++++++ .../R80.40/gwlb/cme-iam-role-gwlb.yaml | 131 ++ .../templates/R80.40/gwlb/gwlb-master.yaml | 732 +++++++++ .../gwlb/gwlb-servers-infrastructure.yaml | 324 ++++ .../gwlb/gwlb-wan-global-network-master.yaml | 847 +++++++++++ .../R80.40/gwlb/gwlb-wan-global-network.yaml | 1317 +++++++++++++++++ .../gwlb/gwlb-wan-security-vpc-master.yaml | 874 +++++++++++ .../R80.40/gwlb/gwlb-wan-security-vpc.yaml | 1241 ++++++++++++++++ .../aws/templates/R80.40/gwlb/gwlb.yaml | 732 +++++++++ .../R80.40/gwlb/management-gwlb.yaml | 584 ++++++++ .../R80.40/gwlb/tgw-gwlb-master.yaml | 873 +++++++++++ .../aws/templates/R80.40/gwlb/tgw-gwlb.yaml | 1221 +++++++++++++++ .../R80.40/iam/cloudwatch-policy.yaml | 39 + .../R80.40/iam/cluster-iam-role.yaml | 35 + .../templates/R80.40/iam/cme-iam-role.yaml | 159 ++ .../aws/templates/R80.40/iam/sts-role.yaml | 119 ++ .../R80.40/management/management.yaml | 585 ++++++++ .../aws/templates/R80.40/management/mds.yaml | 529 +++++++ .../R80.40/utils/copy-lambda-zip.yaml | 138 ++ .../R80.40/utils/tap-target-and-filter.yaml | 68 + .../aws/templates/R80.40/utils/vpc.yaml | 571 +++++++ .../{ => R80}/management-r80/README.md | 0 .../{ => R80}/management-r80/r80.json | 0 .../templates/R81/autoscale/autoscale.yaml | 612 ++++++++ .../R81/autoscale/custom-autoscale.yaml | 226 +++ .../R81/autoscale/tgw-asg-master.yaml | 690 +++++++++ .../aws/templates/R81/autoscale/tgw-asg.yaml | 682 +++++++++ .../templates/R81/cluster/cluster-master.yaml | 512 +++++++ .../aws/templates/R81/cluster/cluster.yaml | 762 ++++++++++ .../R81/cluster/cross-az-cluster.yaml | 775 ++++++++++ .../R81/cluster/geo-cluster-master.yaml | 523 +++++++ .../templates/R81/cluster/geo-cluster.yaml | 734 +++++++++ .../R81/cluster/tgw-cross-az-cluster.yaml | 535 +++++++ .../templates/R81/cluster/tgw-ha-master.yaml | 531 +++++++ .../aws/templates/R81/cluster/tgw-ha.yaml | 527 +++++++ .../templates/R81/gateway/gateway-master.yaml | 495 +++++++ .../aws/templates/R81/gateway/gateway.yaml | 601 ++++++++ .../R81/gateway/standalone-master.yaml | 443 ++++++ .../aws/templates/R81/gateway/standalone.yaml | 538 +++++++ .../templates/R81/iam/cloudwatch-policy.yaml | 39 + .../templates/R81/iam/cluster-iam-role.yaml | 35 + .../aws/templates/R81/iam/cme-iam-role.yaml | 159 ++ .../aws/templates/R81/iam/sts-role.yaml | 119 ++ .../templates/R81/management/management.yaml | 585 ++++++++ .../aws/templates/R81/management/mds.yaml | 529 +++++++ .../templates/R81/utils/copy-lambda-zip.yaml | 138 ++ .../R81/utils/tap-target-and-filter.yaml | 68 + deprecated/aws/templates/R81/utils/vpc.yaml | 571 +++++++ .../ali/R81/cluster-master/README.md | 174 +++ .../ali/R81/cluster-master/locals.tf | 28 + .../terraform/ali/R81/cluster-master/main.tf | 53 + .../ali/R81/cluster-master/output.tf | 48 + .../ali/R81/cluster-master/terraform.tfvars | 47 + .../ali/R81/cluster-master/variables.tf | 150 ++ .../ali/R81/cluster-master/versions.tf | 9 + .../terraform/ali/R81/cluster/README.md | 158 ++ .../cluster/cluster_member_a_userdata.yaml | 4 + .../cluster/cluster_member_b_userdata.yaml | 4 + .../terraform/ali/R81/cluster/locals.tf | 46 + deprecated/terraform/ali/R81/cluster/main.tf | 178 +++ .../terraform/ali/R81/cluster/output.tf | 33 + .../ali/R81/cluster/terraform.tfvars | 40 + .../terraform/ali/R81/cluster/variables.tf | 144 ++ .../terraform/ali/R81/cluster/versions.tf | 9 + .../ali/R81/gateway-master/README.md | 155 ++ .../ali/R81/gateway-master/locals.tf | 17 + .../terraform/ali/R81/gateway-master/main.tf | 49 + .../ali/R81/gateway-master/output.tf | 33 + .../ali/R81/gateway-master/terraform.tfvars | 42 + .../ali/R81/gateway-master/variables.tf | 140 ++ .../ali/R81/gateway-master/versions.tf | 9 + .../terraform/ali/R81/gateway/README.md | 141 ++ .../terraform/ali/R81/gateway/locals.tf | 23 + deprecated/terraform/ali/R81/gateway/main.tf | 70 + .../terraform/ali/R81/gateway/output.tf | 21 + .../ali/R81/gateway/terraform.tfvars | 37 + .../terraform/ali/R81/gateway/variables.tf | 133 ++ .../terraform/ali/R81/gateway/versions.tf | 9 + .../ali/R81/management-master/README.md | 134 ++ .../ali/R81/management-master/locals.tf | 20 + .../ali/R81/management-master/main.tf | 40 + .../ali/R81/management-master/output.tf | 25 + .../R81/management-master/terraform.tfvars | 40 + .../ali/R81/management-master/variables.tf | 137 ++ .../ali/R81/management-master/versions.tf | 9 + .../terraform/ali/R81/management/README.md | 127 ++ .../terraform/ali/R81/management/locals.tf | 24 + .../terraform/ali/R81/management/main.tf | 177 +++ .../R81/management/management_userdata.yaml | 4 + .../terraform/ali/R81/management/output.tf | 19 + .../ali/R81/management/terraform.tfvars | 35 + .../terraform/ali/R81/management/variables.tf | 128 ++ .../terraform/ali/R81/management/versions.tf | 9 + .../R81/modules/cluster-ram-role/locals.tf | 5 + .../ali/R81/modules/cluster-ram-role/main.tf | 54 + .../R81/modules/cluster-ram-role/output.tf | 9 + .../R81/modules/cluster-ram-role/variables.tf | 5 + .../R81/modules/cluster-ram-role/versions.tf | 9 + .../R81/modules/common/elastic_ip/locals.tf | 12 + .../ali/R81/modules/common/elastic_ip/main.tf | 10 + .../R81/modules/common/elastic_ip/output.tf | 7 + .../modules/common/elastic_ip/variables.tf | 22 + .../R81/modules/common/elastic_ip/versions.tf | 9 + .../gateway_instance/gateway_userdata.yaml | 4 + .../modules/common/gateway_instance/locals.tf | 22 + .../modules/common/gateway_instance/main.tf | 28 + .../modules/common/gateway_instance/output.tf | 6 + .../common/gateway_instance/variables.tf | 100 ++ .../common/gateway_instance/versions.tf | 9 + .../R81/modules/common/instance_type/main.tf | 28 + .../modules/common/instance_type/variables.tf | 20 + .../modules/common/instance_type/versions.tf | 3 + .../common/internal_default_route/locals.tf | 3 + .../common/internal_default_route/main.tf | 7 + .../common/internal_default_route/output.tf | 3 + .../internal_default_route/variables.tf | 9 + .../common/internal_default_route/versions.tf | 9 + .../R81/modules/common/permissive_sg/main.tf | 27 + .../modules/common/permissive_sg/output.tf | 6 + .../modules/common/permissive_sg/variables.tf | 13 + .../modules/common/permissive_sg/versions.tf | 9 + .../modules/common/version_license/main.tf | 23 + .../common/version_license/variables.tf | 19 + .../common/version_license/versions.tf | 9 + .../ali/R81/modules/images/images.yaml | 210 +++ .../terraform/ali/R81/modules/images/main.tf | 20 + .../ali/R81/modules/images/output.tf | 6 + .../ali/R81/modules/images/variables.tf | 20 + .../ali/R81/modules/images/versions.tf | 3 + .../terraform/ali/R81/modules/vpc/locals.tf | 6 + .../terraform/ali/R81/modules/vpc/main.tf | 38 + .../terraform/ali/R81/modules/vpc/output.tf | 15 + .../ali/R81/modules/vpc/variables.tf | 23 + .../terraform/ali/R81/modules/vpc/versions.tf | 9 + .../aws/R80.40/autoscale-gwlb/README.md | 185 +++ .../R80.40/autoscale-gwlb/asg_userdata.yaml | 29 + .../aws/R80.40/autoscale-gwlb/locals.tf | 56 + .../aws/R80.40/autoscale-gwlb/main.tf | 202 +++ .../aws/R80.40/autoscale-gwlb/output.tf | 41 + .../R80.40/autoscale-gwlb/terraform.tfvars | 42 + .../aws/R80.40/autoscale-gwlb/variables.tf | 191 +++ .../aws/R80.40/autoscale-gwlb/versions.tf | 15 + .../terraform/aws/R80.40/autoscale/README.md | 199 +++ .../aws/R80.40/autoscale/asg_userdata.yaml | 4 + .../terraform/aws/R80.40/autoscale/locals.tf | 62 + .../terraform/aws/R80.40/autoscale/main.tf | 248 ++++ .../terraform/aws/R80.40/autoscale/output.tf | 43 + .../aws/R80.40/autoscale/terraform.tfvars | 45 + .../aws/R80.40/autoscale/variables.tf | 190 +++ .../aws/R80.40/autoscale/versions.tf | 15 + .../aws/R80.40/cluster-master/README.md | 221 +++ .../aws/R80.40/cluster-master/locals.tf | 52 + .../aws/R80.40/cluster-master/main.tf | 64 + .../aws/R80.40/cluster-master/output.tf | 24 + .../R80.40/cluster-master/terraform.tfvars | 47 + .../aws/R80.40/cluster-master/variables.tf | 183 +++ .../aws/R80.40/cluster-master/versions.tf | 12 + .../terraform/aws/R80.40/cluster/README.md | 201 +++ .../cluster/cluster_member_a_userdata.yaml | 4 + .../cluster/cluster_member_b_userdata.yaml | 4 + .../terraform/aws/R80.40/cluster/locals.tf | 69 + .../terraform/aws/R80.40/cluster/main.tf | 291 ++++ .../terraform/aws/R80.40/cluster/output.tf | 24 + .../aws/R80.40/cluster/terraform.tfvars | 43 + .../terraform/aws/R80.40/cluster/variables.tf | 181 +++ .../terraform/aws/R80.40/cluster/versions.tf | 12 + .../aws/R80.40/cme-iam-role-gwlb/README.md | 100 ++ .../aws/R80.40/cme-iam-role-gwlb/main.tf | 110 ++ .../aws/R80.40/cme-iam-role-gwlb/output.tf | 13 + .../R80.40/cme-iam-role-gwlb/terraform.tfvars | 5 + .../aws/R80.40/cme-iam-role-gwlb/variables.tf | 42 + .../aws/R80.40/cme-iam-role-gwlb/versions.tf | 9 + .../aws/R80.40/cme-iam-role/README.md | 102 ++ .../terraform/aws/R80.40/cme-iam-role/main.tf | 136 ++ .../aws/R80.40/cme-iam-role/output.tf | 12 + .../aws/R80.40/cme-iam-role/terraform.tfvars | 5 + .../aws/R80.40/cme-iam-role/variables.tf | 42 + .../aws/R80.40/cme-iam-role/versions.tf | 9 + .../R80.40/cross-az-cluster-master/README.md | 219 +++ .../R80.40/cross-az-cluster-master/locals.tf | 58 + .../R80.40/cross-az-cluster-master/main.tf | 70 + .../R80.40/cross-az-cluster-master/output.tf | 24 + .../cross-az-cluster-master/terraform.tfvars | 48 + .../cross-az-cluster-master/variables.tf | 183 +++ .../cross-az-cluster-master/versions.tf | 12 + .../aws/R80.40/cross-az-cluster/README.md | 196 +++ .../cluster_member_a_userdata.yaml | 4 + .../cluster_member_b_userdata.yaml | 4 + .../aws/R80.40/cross-az-cluster/locals.tf | 75 + .../aws/R80.40/cross-az-cluster/main.tf | 294 ++++ .../aws/R80.40/cross-az-cluster/output.tf | 30 + .../R80.40/cross-az-cluster/terraform.tfvars | 42 + .../aws/R80.40/cross-az-cluster/variables.tf | 181 +++ .../aws/R80.40/cross-az-cluster/versions.tf | 12 + .../aws/R80.40/gateway-master/README.md | 216 +++ .../aws/R80.40/gateway-master/locals.tf | 48 + .../aws/R80.40/gateway-master/main.tf | 66 + .../aws/R80.40/gateway-master/output.tf | 33 + .../R80.40/gateway-master/terraform.tfvars | 50 + .../aws/R80.40/gateway-master/variables.tf | 195 +++ .../aws/R80.40/gateway-master/versions.tf | 12 + .../terraform/aws/R80.40/gateway/README.md | 191 +++ .../terraform/aws/R80.40/gateway/locals.tf | 48 + .../terraform/aws/R80.40/gateway/main.tf | 119 ++ .../terraform/aws/R80.40/gateway/output.tf | 21 + .../aws/R80.40/gateway/terraform.tfvars | 46 + .../terraform/aws/R80.40/gateway/variables.tf | 192 +++ .../terraform/aws/R80.40/gateway/versions.tf | 12 + .../aws/R80.40/gwlb-master/README.md | 235 +++ .../aws/R80.40/gwlb-master/locals.tf | 61 + .../terraform/aws/R80.40/gwlb-master/main.tf | 69 + .../aws/R80.40/gwlb-master/output.tf | 24 + .../aws/R80.40/gwlb-master/terraform.tfvars | 56 + .../aws/R80.40/gwlb-master/variables.tf | 274 ++++ .../aws/R80.40/gwlb-master/versions.tf | 15 + .../terraform/aws/R80.40/gwlb/README.md | 228 +++ .../terraform/aws/R80.40/gwlb/locals.tf | 55 + deprecated/terraform/aws/R80.40/gwlb/main.tf | 99 ++ .../terraform/aws/R80.40/gwlb/output.tf | 22 + .../aws/R80.40/gwlb/terraform.tfvars | 52 + .../terraform/aws/R80.40/gwlb/variables.tf | 263 ++++ .../terraform/aws/R80.40/gwlb/versions.tf | 15 + .../terraform/aws/R80.40/management/README.md | 200 +++ .../terraform/aws/R80.40/management/locals.tf | 76 + .../terraform/aws/R80.40/management/main.tf | 221 +++ .../management/management_userdata.yaml | 4 + .../terraform/aws/R80.40/management/output.tf | 19 + .../aws/R80.40/management/terraform.tfvars | 42 + .../aws/R80.40/management/variables.tf | 194 +++ .../aws/R80.40/management/versions.tf | 12 + deprecated/terraform/aws/R80.40/mds/README.md | 190 +++ deprecated/terraform/aws/R80.40/mds/locals.tf | 69 + deprecated/terraform/aws/R80.40/mds/main.tf | 194 +++ .../aws/R80.40/mds/mds_userdata.yaml | 4 + deprecated/terraform/aws/R80.40/mds/output.tf | 13 + .../terraform/aws/R80.40/mds/terraform.tfvars | 41 + .../terraform/aws/R80.40/mds/variables.tf | 175 +++ .../terraform/aws/R80.40/mds/versions.tf | 12 + .../terraform/aws/R80.40/modules/amis/main.tf | 23 + .../aws/R80.40/modules/amis/output.tf | 6 + .../aws/R80.40/modules/amis/variables.tf | 26 + .../R80.40/modules/cloudwatch-policy/main.tf | 18 + .../modules/cloudwatch-policy/variables.tf | 9 + .../R80.40/modules/cluster-iam-role/main.tf | 38 + .../R80.40/modules/cluster-iam-role/output.tf | 9 + .../modules/common/elastic_ip/locals.tf | 3 + .../R80.40/modules/common/elastic_ip/main.tf | 10 + .../modules/common/elastic_ip/output.tf | 9 + .../modules/common/elastic_ip/variables.tf | 13 + .../gateway_instance/gateway_userdata.yaml | 4 + .../modules/common/gateway_instance/locals.tf | 39 + .../modules/common/gateway_instance/main.tf | 63 + .../modules/common/gateway_instance/output.tf | 9 + .../common/gateway_instance/variables.tf | 147 ++ .../modules/common/instance_type/main.tf | 353 +++++ .../modules/common/instance_type/variables.tf | 22 + .../common/internal_default_route/locals.tf | 3 + .../common/internal_default_route/main.tf | 6 + .../common/internal_default_route/output.tf | 3 + .../internal_default_route/variables.tf | 9 + .../modules/common/load_balancer/main.tf | 36 + .../modules/common/load_balancer/output.tf | 18 + .../modules/common/load_balancer/variables.tf | 62 + .../modules/common/permissive_sg/main.tf | 20 + .../modules/common/permissive_sg/output.tf | 9 + .../modules/common/permissive_sg/variables.tf | 13 + .../modules/common/version_license/main.tf | 71 + .../common/version_license/variables.tf | 21 + .../R80.40/modules/custom-autoscale/locals.tf | 9 + .../R80.40/modules/custom-autoscale/main.tf | 94 ++ .../modules/custom-autoscale/variables.tf | 89 ++ .../terraform/aws/R80.40/modules/vpc/main.tf | 66 + .../aws/R80.40/modules/vpc/output.tf | 18 + .../aws/R80.40/modules/vpc/variables.tf | 22 + .../aws/R80.40/qs-autoscale-master/README.md | 256 ++++ .../aws/R80.40/qs-autoscale-master/locals.tf | 63 + .../aws/R80.40/qs-autoscale-master/main.tf | 60 + .../aws/R80.40/qs-autoscale-master/output.tf | 58 + .../qs-autoscale-master/terraform.tfvars | 57 + .../R80.40/qs-autoscale-master/variables.tf | 240 +++ .../R80.40/qs-autoscale-master/versions.tf | 15 + .../aws/R80.40/qs-autoscale/README.md | 238 +++ .../aws/R80.40/qs-autoscale/locals.tf | 71 + .../terraform/aws/R80.40/qs-autoscale/main.tf | 165 +++ .../aws/R80.40/qs-autoscale/output.tf | 45 + .../aws/R80.40/qs-autoscale/terraform.tfvars | 48 + .../aws/R80.40/qs-autoscale/variables.tf | 231 +++ .../aws/R80.40/qs-autoscale/versions.tf | 15 + .../aws/R80.40/standalone-master/README.md | 201 +++ .../aws/R80.40/standalone-master/locals.tf | 36 + .../aws/R80.40/standalone-master/main.tf | 63 + .../aws/R80.40/standalone-master/output.tf | 27 + .../R80.40/standalone-master/terraform.tfvars | 43 + .../aws/R80.40/standalone-master/variables.tf | 174 +++ .../aws/R80.40/standalone-master/versions.tf | 12 + .../terraform/aws/R80.40/standalone/README.md | 176 +++ .../terraform/aws/R80.40/standalone/locals.tf | 41 + .../terraform/aws/R80.40/standalone/main.tf | 145 ++ .../terraform/aws/R80.40/standalone/output.tf | 15 + .../standalone/standalone_userdata.yaml | 4 + .../aws/R80.40/standalone/terraform.tfvars | 39 + .../aws/R80.40/standalone/variables.tf | 172 +++ .../aws/R80.40/standalone/versions.tf | 12 + .../tap/Check Point NOW onboarding page.docx | Bin 0 -> 287849 bytes .../tap/CheckPoint_NOW_onboarding_page.pdf | Bin 0 -> 390187 bytes deprecated/terraform/aws/R80.40/tap/README.md | 258 ++++ deprecated/terraform/aws/R80.40/tap/main.tf | 301 ++++ deprecated/terraform/aws/R80.40/tap/output.tf | 34 + .../terraform/aws/R80.40/tap/tap_lambda.py | 155 ++ .../aws/R80.40/tap/tap_termination_lambda.py | 26 + .../terraform/aws/R80.40/tap/tap_user_data.sh | 37 + .../terraform/aws/R80.40/tap/terraform.tfvars | 21 + .../terraform/aws/R80.40/tap/variables.tf | 89 ++ .../aws/R80.40/tests/cluster_master_test.go | 100 ++ .../tests/cross_az_cluster_master_test.go | 99 ++ .../aws/R80.40/tests/gateway_master_test.go | 119 ++ .../terraform/aws/R80.40/tests/globals.go | 177 +++ .../aws/R80.40/tests/gwlb_master_test.go | 99 ++ .../R80.40/tests/qs_autoscale_master_test.go | 129 ++ .../R80.40/tests/standalone_master_test.go | 112 ++ .../aws/R80.40/tests/tgw_asg_master_test.go | 95 ++ .../tests/tgw_cross_az_cluster_master_test.go | 103 ++ .../aws/R80.40/tests/tgw_gwlb_master_test.go | 110 ++ .../aws/R80.40/tgw-asg-master/README.md | 223 +++ .../aws/R80.40/tgw-asg-master/locals.tf | 66 + .../aws/R80.40/tgw-asg-master/main.tf | 55 + .../aws/R80.40/tgw-asg-master/output.tf | 24 + .../R80.40/tgw-asg-master/terraform.tfvars | 47 + .../aws/R80.40/tgw-asg-master/variables.tf | 217 +++ .../aws/R80.40/tgw-asg-master/versions.tf | 15 + .../terraform/aws/R80.40/tgw-asg/README.md | 213 +++ .../terraform/aws/R80.40/tgw-asg/locals.tf | 64 + .../terraform/aws/R80.40/tgw-asg/main.tf | 64 + .../terraform/aws/R80.40/tgw-asg/output.tf | 18 + .../aws/R80.40/tgw-asg/terraform.tfvars | 43 + .../terraform/aws/R80.40/tgw-asg/variables.tf | 211 +++ .../terraform/aws/R80.40/tgw-asg/versions.tf | 15 + .../tgw-cross-az-cluster-master/README.md | 208 +++ .../tgw-cross-az-cluster-master/locals.tf | 61 + .../tgw-cross-az-cluster-master/main.tf | 73 + .../tgw-cross-az-cluster-master/output.tf | 30 + .../terraform.tfvars | 48 + .../tgw-cross-az-cluster-master/variables.tf | 200 +++ .../tgw-cross-az-cluster-master/versions.tf | 15 + .../aws/R80.40/tgw-cross-az-cluster/README.md | 204 +++ .../aws/R80.40/tgw-cross-az-cluster/locals.tf | 60 + .../aws/R80.40/tgw-cross-az-cluster/main.tf | 62 + .../aws/R80.40/tgw-cross-az-cluster/output.tf | 27 + .../tgw-cross-az-cluster/terraform.tfvars | 43 + .../R80.40/tgw-cross-az-cluster/variables.tf | 201 +++ .../R80.40/tgw-cross-az-cluster/versions.tf | 15 + .../aws/R80.40/tgw-gwlb-master/README.md | 264 ++++ .../aws/R80.40/tgw-gwlb-master/locals.tf | 62 + .../aws/R80.40/tgw-gwlb-master/main.tf | 85 ++ .../aws/R80.40/tgw-gwlb-master/output.tf | 24 + .../R80.40/tgw-gwlb-master/terraform.tfvars | 76 + .../aws/R80.40/tgw-gwlb-master/variables.tf | 326 ++++ .../aws/R80.40/tgw-gwlb-master/versions.tf | 15 + .../terraform/aws/R80.40/tgw-gwlb/README.md | 263 ++++ .../terraform/aws/R80.40/tgw-gwlb/locals.tf | 60 + .../terraform/aws/R80.40/tgw-gwlb/main.tf | 438 ++++++ .../terraform/aws/R80.40/tgw-gwlb/output.tf | 24 + .../aws/R80.40/tgw-gwlb/terraform.tfvars | 69 + .../aws/R80.40/tgw-gwlb/variables.tf | 333 +++++ .../terraform/aws/R80.40/tgw-gwlb/versions.tf | 15 + .../aws/R81/autoscale-gwlb/README.md | 186 +++ .../aws/R81/autoscale-gwlb/asg_userdata.yaml | 29 + .../aws/R81/autoscale-gwlb/locals.tf | 55 + .../terraform/aws/R81/autoscale-gwlb/main.tf | 202 +++ .../aws/R81/autoscale-gwlb/output.tf | 41 + .../aws/R81/autoscale-gwlb/terraform.tfvars | 42 + .../aws/R81/autoscale-gwlb/variables.tf | 191 +++ .../aws/R81/autoscale-gwlb/versions.tf | 15 + .../terraform/aws/R81/autoscale/README.md | 201 +++ .../aws/R81/autoscale/asg_userdata.yaml | 4 + .../terraform/aws/R81/autoscale/locals.tf | 62 + .../terraform/aws/R81/autoscale/main.tf | 248 ++++ .../terraform/aws/R81/autoscale/output.tf | 43 + .../aws/R81/autoscale/terraform.tfvars | 45 + .../terraform/aws/R81/autoscale/variables.tf | 190 +++ .../terraform/aws/R81/autoscale/versions.tf | 15 + .../aws/R81/cluster-master/README.md | 221 +++ .../aws/R81/cluster-master/locals.tf | 52 + .../terraform/aws/R81/cluster-master/main.tf | 64 + .../aws/R81/cluster-master/output.tf | 24 + .../aws/R81/cluster-master/terraform.tfvars | 47 + .../aws/R81/cluster-master/variables.tf | 183 +++ .../aws/R81/cluster-master/versions.tf | 12 + .../terraform/aws/R81/cluster/README.md | 202 +++ .../cluster/cluster_member_a_userdata.yaml | 4 + .../cluster/cluster_member_b_userdata.yaml | 4 + .../terraform/aws/R81/cluster/locals.tf | 69 + deprecated/terraform/aws/R81/cluster/main.tf | 291 ++++ .../terraform/aws/R81/cluster/output.tf | 24 + .../aws/R81/cluster/terraform.tfvars | 43 + .../terraform/aws/R81/cluster/variables.tf | 181 +++ .../terraform/aws/R81/cluster/versions.tf | 12 + .../aws/R81/cme-iam-role-gwlb/README.md | 100 ++ .../aws/R81/cme-iam-role-gwlb/main.tf | 110 ++ .../aws/R81/cme-iam-role-gwlb/output.tf | 13 + .../R81/cme-iam-role-gwlb/terraform.tfvars | 5 + .../aws/R81/cme-iam-role-gwlb/variables.tf | 42 + .../aws/R81/cme-iam-role-gwlb/versions.tf | 9 + .../terraform/aws/R81/cme-iam-role/README.md | 102 ++ .../terraform/aws/R81/cme-iam-role/main.tf | 136 ++ .../terraform/aws/R81/cme-iam-role/output.tf | 12 + .../aws/R81/cme-iam-role/terraform.tfvars | 5 + .../aws/R81/cme-iam-role/variables.tf | 42 + .../aws/R81/cme-iam-role/versions.tf | 9 + .../aws/R81/cross-az-cluster-master/README.md | 219 +++ .../aws/R81/cross-az-cluster-master/locals.tf | 58 + .../aws/R81/cross-az-cluster-master/main.tf | 70 + .../aws/R81/cross-az-cluster-master/output.tf | 24 + .../cross-az-cluster-master/terraform.tfvars | 48 + .../R81/cross-az-cluster-master/variables.tf | 183 +++ .../R81/cross-az-cluster-master/versions.tf | 12 + .../aws/R81/cross-az-cluster/README.md | 196 +++ .../cluster_member_a_userdata.yaml | 4 + .../cluster_member_b_userdata.yaml | 4 + .../aws/R81/cross-az-cluster/locals.tf | 75 + .../aws/R81/cross-az-cluster/main.tf | 294 ++++ .../aws/R81/cross-az-cluster/output.tf | 30 + .../aws/R81/cross-az-cluster/terraform.tfvars | 42 + .../aws/R81/cross-az-cluster/variables.tf | 181 +++ .../aws/R81/cross-az-cluster/versions.tf | 12 + .../aws/R81/gateway-master/README.md | 217 +++ .../aws/R81/gateway-master/locals.tf | 48 + .../terraform/aws/R81/gateway-master/main.tf | 66 + .../aws/R81/gateway-master/output.tf | 33 + .../aws/R81/gateway-master/terraform.tfvars | 50 + .../aws/R81/gateway-master/variables.tf | 195 +++ .../aws/R81/gateway-master/versions.tf | 12 + .../terraform/aws/R81/gateway/README.md | 192 +++ .../terraform/aws/R81/gateway/locals.tf | 48 + deprecated/terraform/aws/R81/gateway/main.tf | 119 ++ .../terraform/aws/R81/gateway/output.tf | 21 + .../aws/R81/gateway/terraform.tfvars | 46 + .../terraform/aws/R81/gateway/variables.tf | 192 +++ .../terraform/aws/R81/gateway/versions.tf | 12 + .../terraform/aws/R81/gwlb-master/README.md | 236 +++ .../terraform/aws/R81/gwlb-master/locals.tf | 61 + .../terraform/aws/R81/gwlb-master/main.tf | 69 + .../terraform/aws/R81/gwlb-master/output.tf | 24 + .../aws/R81/gwlb-master/terraform.tfvars | 56 + .../aws/R81/gwlb-master/variables.tf | 274 ++++ .../terraform/aws/R81/gwlb-master/versions.tf | 15 + deprecated/terraform/aws/R81/gwlb/README.md | 229 +++ deprecated/terraform/aws/R81/gwlb/locals.tf | 55 + deprecated/terraform/aws/R81/gwlb/main.tf | 99 ++ deprecated/terraform/aws/R81/gwlb/output.tf | 22 + .../terraform/aws/R81/gwlb/terraform.tfvars | 52 + .../terraform/aws/R81/gwlb/variables.tf | 263 ++++ deprecated/terraform/aws/R81/gwlb/versions.tf | 15 + .../terraform/aws/R81/management/README.md | 201 +++ .../terraform/aws/R81/management/locals.tf | 76 + .../terraform/aws/R81/management/main.tf | 221 +++ .../R81/management/management_userdata.yaml | 4 + .../terraform/aws/R81/management/output.tf | 19 + .../aws/R81/management/terraform.tfvars | 42 + .../terraform/aws/R81/management/variables.tf | 194 +++ .../terraform/aws/R81/management/versions.tf | 12 + deprecated/terraform/aws/R81/mds/README.md | 191 +++ deprecated/terraform/aws/R81/mds/locals.tf | 69 + deprecated/terraform/aws/R81/mds/main.tf | 194 +++ .../terraform/aws/R81/mds/mds_userdata.yaml | 4 + deprecated/terraform/aws/R81/mds/output.tf | 13 + .../terraform/aws/R81/mds/terraform.tfvars | 41 + deprecated/terraform/aws/R81/mds/variables.tf | 175 +++ deprecated/terraform/aws/R81/mds/versions.tf | 12 + .../terraform/aws/R81/modules/amis/main.tf | 23 + .../terraform/aws/R81/modules/amis/output.tf | 6 + .../aws/R81/modules/amis/variables.tf | 26 + .../aws/R81/modules/cloudwatch-policy/main.tf | 18 + .../modules/cloudwatch-policy/variables.tf | 9 + .../aws/R81/modules/cluster-iam-role/main.tf | 38 + .../R81/modules/cluster-iam-role/output.tf | 9 + .../R81/modules/common/elastic_ip/locals.tf | 3 + .../aws/R81/modules/common/elastic_ip/main.tf | 10 + .../R81/modules/common/elastic_ip/output.tf | 9 + .../modules/common/elastic_ip/variables.tf | 13 + .../gateway_instance/gateway_userdata.yaml | 4 + .../modules/common/gateway_instance/locals.tf | 39 + .../modules/common/gateway_instance/main.tf | 63 + .../modules/common/gateway_instance/output.tf | 9 + .../common/gateway_instance/variables.tf | 147 ++ .../R81/modules/common/instance_type/main.tf | 353 +++++ .../modules/common/instance_type/variables.tf | 22 + .../common/internal_default_route/locals.tf | 3 + .../common/internal_default_route/main.tf | 6 + .../common/internal_default_route/output.tf | 3 + .../internal_default_route/variables.tf | 9 + .../R81/modules/common/load_balancer/main.tf | 36 + .../modules/common/load_balancer/output.tf | 18 + .../modules/common/load_balancer/variables.tf | 62 + .../R81/modules/common/permissive_sg/main.tf | 20 + .../modules/common/permissive_sg/output.tf | 9 + .../modules/common/permissive_sg/variables.tf | 13 + .../modules/common/version_license/main.tf | 60 + .../common/version_license/variables.tf | 21 + .../R81/modules/custom-autoscale/locals.tf | 9 + .../aws/R81/modules/custom-autoscale/main.tf | 94 ++ .../R81/modules/custom-autoscale/variables.tf | 89 ++ .../terraform/aws/R81/modules/vpc/main.tf | 66 + .../terraform/aws/R81/modules/vpc/output.tf | 18 + .../aws/R81/modules/vpc/variables.tf | 22 + .../aws/R81/qs-autoscale-master/README.md | 256 ++++ .../aws/R81/qs-autoscale-master/locals.tf | 63 + .../aws/R81/qs-autoscale-master/main.tf | 60 + .../aws/R81/qs-autoscale-master/output.tf | 58 + .../R81/qs-autoscale-master/terraform.tfvars | 57 + .../aws/R81/qs-autoscale-master/variables.tf | 240 +++ .../aws/R81/qs-autoscale-master/versions.tf | 15 + .../terraform/aws/R81/qs-autoscale/README.md | 238 +++ .../terraform/aws/R81/qs-autoscale/locals.tf | 71 + .../terraform/aws/R81/qs-autoscale/main.tf | 165 +++ .../terraform/aws/R81/qs-autoscale/output.tf | 45 + .../aws/R81/qs-autoscale/terraform.tfvars | 48 + .../aws/R81/qs-autoscale/variables.tf | 231 +++ .../aws/R81/qs-autoscale/versions.tf | 15 + .../aws/R81/standalone-master/README.md | 202 +++ .../aws/R81/standalone-master/locals.tf | 36 + .../aws/R81/standalone-master/main.tf | 63 + .../aws/R81/standalone-master/output.tf | 27 + .../R81/standalone-master/terraform.tfvars | 43 + .../aws/R81/standalone-master/variables.tf | 174 +++ .../aws/R81/standalone-master/versions.tf | 12 + .../terraform/aws/R81/standalone/README.md | 178 +++ .../terraform/aws/R81/standalone/locals.tf | 41 + .../terraform/aws/R81/standalone/main.tf | 145 ++ .../terraform/aws/R81/standalone/output.tf | 15 + .../R81/standalone/standalone_userdata.yaml | 4 + .../aws/R81/standalone/terraform.tfvars | 39 + .../terraform/aws/R81/standalone/variables.tf | 172 +++ .../terraform/aws/R81/standalone/versions.tf | 12 + .../aws/R81/tests/cluster_master_test.go | 100 ++ .../R81/tests/cross_az_cluster_master_test.go | 99 ++ .../aws/R81/tests/gateway_master_test.go | 119 ++ deprecated/terraform/aws/R81/tests/globals.go | 177 +++ .../aws/R81/tests/gwlb_master_test.go | 99 ++ .../aws/R81/tests/qs_autoscale_master_test.go | 129 ++ .../aws/R81/tests/standalone_master_test.go | 112 ++ .../aws/R81/tests/tgw_asg_master_test.go | 95 ++ .../tests/tgw_cross_az_cluster_master_test.go | 103 ++ .../aws/R81/tests/tgw_gwlb_master_test.go | 110 ++ .../aws/R81/tgw-asg-master/README.md | 224 +++ .../aws/R81/tgw-asg-master/locals.tf | 66 + .../terraform/aws/R81/tgw-asg-master/main.tf | 55 + .../aws/R81/tgw-asg-master/output.tf | 24 + .../aws/R81/tgw-asg-master/terraform.tfvars | 47 + .../aws/R81/tgw-asg-master/variables.tf | 217 +++ .../aws/R81/tgw-asg-master/versions.tf | 15 + .../terraform/aws/R81/tgw-asg/README.md | 214 +++ .../terraform/aws/R81/tgw-asg/locals.tf | 64 + deprecated/terraform/aws/R81/tgw-asg/main.tf | 64 + .../terraform/aws/R81/tgw-asg/output.tf | 18 + .../aws/R81/tgw-asg/terraform.tfvars | 43 + .../terraform/aws/R81/tgw-asg/variables.tf | 211 +++ .../terraform/aws/R81/tgw-asg/versions.tf | 15 + .../R81/tgw-cross-az-cluster-master/README.md | 208 +++ .../R81/tgw-cross-az-cluster-master/locals.tf | 61 + .../R81/tgw-cross-az-cluster-master/main.tf | 73 + .../R81/tgw-cross-az-cluster-master/output.tf | 30 + .../terraform.tfvars | 48 + .../tgw-cross-az-cluster-master/variables.tf | 200 +++ .../tgw-cross-az-cluster-master/versions.tf | 15 + .../aws/R81/tgw-cross-az-cluster/README.md | 204 +++ .../aws/R81/tgw-cross-az-cluster/locals.tf | 60 + .../aws/R81/tgw-cross-az-cluster/main.tf | 62 + .../aws/R81/tgw-cross-az-cluster/output.tf | 27 + .../R81/tgw-cross-az-cluster/terraform.tfvars | 43 + .../aws/R81/tgw-cross-az-cluster/variables.tf | 201 +++ .../aws/R81/tgw-cross-az-cluster/versions.tf | 15 + .../aws/R81/tgw-gwlb-master/README.md | 265 ++++ .../aws/R81/tgw-gwlb-master/locals.tf | 62 + .../terraform/aws/R81/tgw-gwlb-master/main.tf | 85 ++ .../aws/R81/tgw-gwlb-master/output.tf | 24 + .../aws/R81/tgw-gwlb-master/terraform.tfvars | 76 + .../aws/R81/tgw-gwlb-master/variables.tf | 326 ++++ .../aws/R81/tgw-gwlb-master/versions.tf | 15 + .../terraform/aws/R81/tgw-gwlb/README.md | 264 ++++ .../terraform/aws/R81/tgw-gwlb/locals.tf | 60 + deprecated/terraform/aws/R81/tgw-gwlb/main.tf | 438 ++++++ .../terraform/aws/R81/tgw-gwlb/output.tf | 24 + .../aws/R81/tgw-gwlb/terraform.tfvars | 69 + .../terraform/aws/R81/tgw-gwlb/variables.tf | 333 +++++ .../terraform/aws/R81/tgw-gwlb/versions.tf | 15 + 639 files changed, 74093 insertions(+), 6 deletions(-) rename deprecated/aws/templates/{ => R77.30}/gateway-r7730/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R77.30}/gateway-r7730/gateway-2-nic-existing-vpc.json (100%) rename deprecated/aws/templates/{ => R77.30}/gateways-r7730/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R77.30}/gateways-r7730/inter-az-cluster.json (100%) rename deprecated/aws/templates/{ => R77.30}/instance-r7730/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R77.30}/instance-r7730/gwinvpc.json (100%) rename deprecated/aws/templates/{ => R77.30}/management-r7730/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R77.30}/management-r7730/r7730-management.json (100%) rename deprecated/aws/templates/{ => R80.30}/asg-r8030/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/asg-r8030/autoscale.json (100%) rename deprecated/aws/templates/{ => R80.30}/cluster-r8030/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/cluster-r8030/cluster-into-vpc.json (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/cluster-r8030/cluster.json (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/management-r8030/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/management-r8030/management.json (100%) rename deprecated/aws/templates/{ => R80.30}/mds-r8030/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/mds-r8030/mds.json (100%) rename deprecated/aws/templates/{ => R80.30}/single-gw-r8030/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/single-gw-r8030/gateway-into-vpc.json (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/single-gw-r8030/gateway.json (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/tgw-asg-r8030/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/tgw-asg-r8030/checkpoint-tgw-asg-master.yaml (100%) rename deprecated/aws/templates/{ => R80.30}/tgw-asg-r8030/checkpoint-tgw-asg.yaml (100%) rename deprecated/aws/templates/{ => R80.30}/transit-vpc-r8030/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80.30}/transit-vpc-r8030/checkpoint-transit-master.yaml (100%) rename deprecated/aws/templates/{ => R80.30}/transit-vpc-r8030/checkpoint-transit.yaml (100%) rename deprecated/aws/templates/{ => R80.30}/transit-vpc-r8030/transit-master.yaml (100%) rename deprecated/aws/templates/{ => R80.30}/transit-vpc-r8030/transit.yaml (100%) create mode 100755 deprecated/aws/templates/R80.40/autoscale/autoscale.yaml create mode 100755 deprecated/aws/templates/R80.40/autoscale/custom-autoscale.yaml create mode 100755 deprecated/aws/templates/R80.40/autoscale/tgw-asg-master.yaml create mode 100755 deprecated/aws/templates/R80.40/autoscale/tgw-asg.yaml create mode 100755 deprecated/aws/templates/R80.40/cluster/cluster-master.yaml create mode 100755 deprecated/aws/templates/R80.40/cluster/cluster.yaml create mode 100755 deprecated/aws/templates/R80.40/cluster/geo-cluster-master.yaml create mode 100755 deprecated/aws/templates/R80.40/cluster/geo-cluster.yaml create mode 100755 deprecated/aws/templates/R80.40/cluster/tgw-ha-master.yaml create mode 100755 deprecated/aws/templates/R80.40/cluster/tgw-ha.yaml create mode 100755 deprecated/aws/templates/R80.40/gateway/gateway-master.yaml create mode 100755 deprecated/aws/templates/R80.40/gateway/gateway.yaml create mode 100755 deprecated/aws/templates/R80.40/gateway/standalone-master.yaml create mode 100755 deprecated/aws/templates/R80.40/gateway/standalone.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/amis-gwlb.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/autoscale-gwlb.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/cme-iam-role-gwlb.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/gwlb-master.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/gwlb-servers-infrastructure.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network-master.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc-master.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/gwlb.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/management-gwlb.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/tgw-gwlb-master.yaml create mode 100755 deprecated/aws/templates/R80.40/gwlb/tgw-gwlb.yaml create mode 100755 deprecated/aws/templates/R80.40/iam/cloudwatch-policy.yaml create mode 100755 deprecated/aws/templates/R80.40/iam/cluster-iam-role.yaml create mode 100755 deprecated/aws/templates/R80.40/iam/cme-iam-role.yaml create mode 100755 deprecated/aws/templates/R80.40/iam/sts-role.yaml create mode 100755 deprecated/aws/templates/R80.40/management/management.yaml create mode 100755 deprecated/aws/templates/R80.40/management/mds.yaml create mode 100755 deprecated/aws/templates/R80.40/utils/copy-lambda-zip.yaml create mode 100755 deprecated/aws/templates/R80.40/utils/tap-target-and-filter.yaml create mode 100755 deprecated/aws/templates/R80.40/utils/vpc.yaml rename deprecated/aws/templates/{ => R80}/management-r80/README.md (100%) mode change 100644 => 100755 rename deprecated/aws/templates/{ => R80}/management-r80/r80.json (100%) create mode 100755 deprecated/aws/templates/R81/autoscale/autoscale.yaml create mode 100755 deprecated/aws/templates/R81/autoscale/custom-autoscale.yaml create mode 100755 deprecated/aws/templates/R81/autoscale/tgw-asg-master.yaml create mode 100755 deprecated/aws/templates/R81/autoscale/tgw-asg.yaml create mode 100755 deprecated/aws/templates/R81/cluster/cluster-master.yaml create mode 100755 deprecated/aws/templates/R81/cluster/cluster.yaml create mode 100755 deprecated/aws/templates/R81/cluster/cross-az-cluster.yaml create mode 100755 deprecated/aws/templates/R81/cluster/geo-cluster-master.yaml create mode 100755 deprecated/aws/templates/R81/cluster/geo-cluster.yaml create mode 100755 deprecated/aws/templates/R81/cluster/tgw-cross-az-cluster.yaml create mode 100755 deprecated/aws/templates/R81/cluster/tgw-ha-master.yaml create mode 100755 deprecated/aws/templates/R81/cluster/tgw-ha.yaml create mode 100755 deprecated/aws/templates/R81/gateway/gateway-master.yaml create mode 100755 deprecated/aws/templates/R81/gateway/gateway.yaml create mode 100755 deprecated/aws/templates/R81/gateway/standalone-master.yaml create mode 100755 deprecated/aws/templates/R81/gateway/standalone.yaml create mode 100755 deprecated/aws/templates/R81/iam/cloudwatch-policy.yaml create mode 100755 deprecated/aws/templates/R81/iam/cluster-iam-role.yaml create mode 100755 deprecated/aws/templates/R81/iam/cme-iam-role.yaml create mode 100755 deprecated/aws/templates/R81/iam/sts-role.yaml create mode 100755 deprecated/aws/templates/R81/management/management.yaml create mode 100755 deprecated/aws/templates/R81/management/mds.yaml create mode 100755 deprecated/aws/templates/R81/utils/copy-lambda-zip.yaml create mode 100755 deprecated/aws/templates/R81/utils/tap-target-and-filter.yaml create mode 100755 deprecated/aws/templates/R81/utils/vpc.yaml create mode 100755 deprecated/terraform/ali/R81/cluster-master/README.md create mode 100755 deprecated/terraform/ali/R81/cluster-master/locals.tf create mode 100755 deprecated/terraform/ali/R81/cluster-master/main.tf create mode 100755 deprecated/terraform/ali/R81/cluster-master/output.tf create mode 100755 deprecated/terraform/ali/R81/cluster-master/terraform.tfvars create mode 100755 deprecated/terraform/ali/R81/cluster-master/variables.tf create mode 100755 deprecated/terraform/ali/R81/cluster-master/versions.tf create mode 100755 deprecated/terraform/ali/R81/cluster/README.md create mode 100755 deprecated/terraform/ali/R81/cluster/cluster_member_a_userdata.yaml create mode 100755 deprecated/terraform/ali/R81/cluster/cluster_member_b_userdata.yaml create mode 100755 deprecated/terraform/ali/R81/cluster/locals.tf create mode 100755 deprecated/terraform/ali/R81/cluster/main.tf create mode 100755 deprecated/terraform/ali/R81/cluster/output.tf create mode 100755 deprecated/terraform/ali/R81/cluster/terraform.tfvars create mode 100755 deprecated/terraform/ali/R81/cluster/variables.tf create mode 100755 deprecated/terraform/ali/R81/cluster/versions.tf create mode 100755 deprecated/terraform/ali/R81/gateway-master/README.md create mode 100755 deprecated/terraform/ali/R81/gateway-master/locals.tf create mode 100755 deprecated/terraform/ali/R81/gateway-master/main.tf create mode 100755 deprecated/terraform/ali/R81/gateway-master/output.tf create mode 100755 deprecated/terraform/ali/R81/gateway-master/terraform.tfvars create mode 100755 deprecated/terraform/ali/R81/gateway-master/variables.tf create mode 100755 deprecated/terraform/ali/R81/gateway-master/versions.tf create mode 100755 deprecated/terraform/ali/R81/gateway/README.md create mode 100755 deprecated/terraform/ali/R81/gateway/locals.tf create mode 100755 deprecated/terraform/ali/R81/gateway/main.tf create mode 100755 deprecated/terraform/ali/R81/gateway/output.tf create mode 100755 deprecated/terraform/ali/R81/gateway/terraform.tfvars create mode 100755 deprecated/terraform/ali/R81/gateway/variables.tf create mode 100755 deprecated/terraform/ali/R81/gateway/versions.tf create mode 100755 deprecated/terraform/ali/R81/management-master/README.md create mode 100755 deprecated/terraform/ali/R81/management-master/locals.tf create mode 100755 deprecated/terraform/ali/R81/management-master/main.tf create mode 100755 deprecated/terraform/ali/R81/management-master/output.tf create mode 100755 deprecated/terraform/ali/R81/management-master/terraform.tfvars create mode 100755 deprecated/terraform/ali/R81/management-master/variables.tf create mode 100755 deprecated/terraform/ali/R81/management-master/versions.tf create mode 100755 deprecated/terraform/ali/R81/management/README.md create mode 100755 deprecated/terraform/ali/R81/management/locals.tf create mode 100755 deprecated/terraform/ali/R81/management/main.tf create mode 100755 deprecated/terraform/ali/R81/management/management_userdata.yaml create mode 100755 deprecated/terraform/ali/R81/management/output.tf create mode 100755 deprecated/terraform/ali/R81/management/terraform.tfvars create mode 100755 deprecated/terraform/ali/R81/management/variables.tf create mode 100755 deprecated/terraform/ali/R81/management/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/cluster-ram-role/locals.tf create mode 100755 deprecated/terraform/ali/R81/modules/cluster-ram-role/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/cluster-ram-role/output.tf create mode 100755 deprecated/terraform/ali/R81/modules/cluster-ram-role/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/cluster-ram-role/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/elastic_ip/locals.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/elastic_ip/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/elastic_ip/output.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/elastic_ip/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/elastic_ip/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/gateway_instance/gateway_userdata.yaml create mode 100755 deprecated/terraform/ali/R81/modules/common/gateway_instance/locals.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/gateway_instance/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/gateway_instance/output.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/gateway_instance/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/gateway_instance/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/instance_type/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/instance_type/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/instance_type/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/internal_default_route/locals.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/internal_default_route/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/internal_default_route/output.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/internal_default_route/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/internal_default_route/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/permissive_sg/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/permissive_sg/output.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/permissive_sg/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/permissive_sg/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/version_license/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/version_license/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/common/version_license/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/images/images.yaml create mode 100755 deprecated/terraform/ali/R81/modules/images/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/images/output.tf create mode 100755 deprecated/terraform/ali/R81/modules/images/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/images/versions.tf create mode 100755 deprecated/terraform/ali/R81/modules/vpc/locals.tf create mode 100755 deprecated/terraform/ali/R81/modules/vpc/main.tf create mode 100755 deprecated/terraform/ali/R81/modules/vpc/output.tf create mode 100755 deprecated/terraform/ali/R81/modules/vpc/variables.tf create mode 100755 deprecated/terraform/ali/R81/modules/vpc/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/README.md create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/asg_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/main.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/output.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale-gwlb/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale/README.md create mode 100755 deprecated/terraform/aws/R80.40/autoscale/asg_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/autoscale/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale/main.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale/output.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/autoscale/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/autoscale/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/cluster-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/cluster-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster/README.md create mode 100755 deprecated/terraform/aws/R80.40/cluster/cluster_member_a_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/cluster/cluster_member_b_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/cluster/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster/main.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster/output.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/cluster/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/cluster/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/README.md create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/main.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/output.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role/README.md create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role/main.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role/output.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/cme-iam-role/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/README.md create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_a_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_b_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/main.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/output.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/cross-az-cluster/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/gateway-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/gateway-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway/README.md create mode 100755 deprecated/terraform/aws/R80.40/gateway/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway/main.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway/output.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/gateway/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/gateway/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/gwlb-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/gwlb-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb/README.md create mode 100755 deprecated/terraform/aws/R80.40/gwlb/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb/main.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb/output.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/gwlb/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/management/README.md create mode 100755 deprecated/terraform/aws/R80.40/management/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/management/main.tf create mode 100755 deprecated/terraform/aws/R80.40/management/management_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/management/output.tf create mode 100755 deprecated/terraform/aws/R80.40/management/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/management/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/management/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/mds/README.md create mode 100755 deprecated/terraform/aws/R80.40/mds/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/mds/main.tf create mode 100755 deprecated/terraform/aws/R80.40/mds/mds_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/mds/output.tf create mode 100755 deprecated/terraform/aws/R80.40/mds/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/mds/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/mds/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/amis/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/amis/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/amis/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/cluster-iam-role/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/cluster-iam-role/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/elastic_ip/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/elastic_ip/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/elastic_ip/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/elastic_ip/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/gateway_instance/gateway_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/modules/common/gateway_instance/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/gateway_instance/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/gateway_instance/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/gateway_instance/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/instance_type/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/instance_type/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/internal_default_route/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/internal_default_route/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/internal_default_route/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/internal_default_route/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/load_balancer/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/load_balancer/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/load_balancer/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/permissive_sg/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/permissive_sg/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/permissive_sg/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/version_license/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/common/version_license/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/custom-autoscale/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/custom-autoscale/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/custom-autoscale/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/vpc/main.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/vpc/output.tf create mode 100755 deprecated/terraform/aws/R80.40/modules/vpc/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale/README.md create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale/main.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale/output.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/qs-autoscale/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/standalone-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/standalone-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone/README.md create mode 100755 deprecated/terraform/aws/R80.40/standalone/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone/main.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone/output.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone/standalone_userdata.yaml create mode 100755 deprecated/terraform/aws/R80.40/standalone/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/standalone/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/standalone/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/tap/Check Point NOW onboarding page.docx create mode 100755 deprecated/terraform/aws/R80.40/tap/CheckPoint_NOW_onboarding_page.pdf create mode 100755 deprecated/terraform/aws/R80.40/tap/README.md create mode 100755 deprecated/terraform/aws/R80.40/tap/main.tf create mode 100755 deprecated/terraform/aws/R80.40/tap/output.tf create mode 100755 deprecated/terraform/aws/R80.40/tap/tap_lambda.py create mode 100755 deprecated/terraform/aws/R80.40/tap/tap_termination_lambda.py create mode 100755 deprecated/terraform/aws/R80.40/tap/tap_user_data.sh create mode 100755 deprecated/terraform/aws/R80.40/tap/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/tap/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/tests/cluster_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/cross_az_cluster_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/gateway_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/globals.go create mode 100755 deprecated/terraform/aws/R80.40/tests/gwlb_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/qs_autoscale_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/standalone_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/tgw_asg_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/tgw_cross_az_cluster_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tests/tgw_gwlb_master_test.go create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg/README.md create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg/main.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg/output.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-asg/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/README.md create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/main.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/output.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb-master/README.md create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb-master/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb-master/main.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb-master/output.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb-master/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb-master/versions.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb/README.md create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb/locals.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb/main.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb/output.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R80.40/tgw-gwlb/versions.tf create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/README.md create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/asg_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/locals.tf create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/main.tf create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/output.tf create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R81/autoscale-gwlb/versions.tf create mode 100755 deprecated/terraform/aws/R81/autoscale/README.md create mode 100755 deprecated/terraform/aws/R81/autoscale/asg_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/autoscale/locals.tf create mode 100755 deprecated/terraform/aws/R81/autoscale/main.tf create mode 100755 deprecated/terraform/aws/R81/autoscale/output.tf create mode 100755 deprecated/terraform/aws/R81/autoscale/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/autoscale/variables.tf create mode 100755 deprecated/terraform/aws/R81/autoscale/versions.tf create mode 100755 deprecated/terraform/aws/R81/cluster-master/README.md create mode 100755 deprecated/terraform/aws/R81/cluster-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/cluster-master/main.tf create mode 100755 deprecated/terraform/aws/R81/cluster-master/output.tf create mode 100755 deprecated/terraform/aws/R81/cluster-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/cluster-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/cluster-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/cluster/README.md create mode 100755 deprecated/terraform/aws/R81/cluster/cluster_member_a_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/cluster/cluster_member_b_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/cluster/locals.tf create mode 100755 deprecated/terraform/aws/R81/cluster/main.tf create mode 100755 deprecated/terraform/aws/R81/cluster/output.tf create mode 100755 deprecated/terraform/aws/R81/cluster/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/cluster/variables.tf create mode 100755 deprecated/terraform/aws/R81/cluster/versions.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role-gwlb/README.md create mode 100755 deprecated/terraform/aws/R81/cme-iam-role-gwlb/main.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role-gwlb/output.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role-gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/cme-iam-role-gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role-gwlb/versions.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role/README.md create mode 100755 deprecated/terraform/aws/R81/cme-iam-role/main.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role/output.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/cme-iam-role/variables.tf create mode 100755 deprecated/terraform/aws/R81/cme-iam-role/versions.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster-master/README.md create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster-master/main.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster-master/output.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/README.md create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_a_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_b_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/locals.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/main.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/output.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/variables.tf create mode 100755 deprecated/terraform/aws/R81/cross-az-cluster/versions.tf create mode 100755 deprecated/terraform/aws/R81/gateway-master/README.md create mode 100755 deprecated/terraform/aws/R81/gateway-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/gateway-master/main.tf create mode 100755 deprecated/terraform/aws/R81/gateway-master/output.tf create mode 100755 deprecated/terraform/aws/R81/gateway-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/gateway-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/gateway-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/gateway/README.md create mode 100755 deprecated/terraform/aws/R81/gateway/locals.tf create mode 100755 deprecated/terraform/aws/R81/gateway/main.tf create mode 100755 deprecated/terraform/aws/R81/gateway/output.tf create mode 100755 deprecated/terraform/aws/R81/gateway/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/gateway/variables.tf create mode 100755 deprecated/terraform/aws/R81/gateway/versions.tf create mode 100755 deprecated/terraform/aws/R81/gwlb-master/README.md create mode 100755 deprecated/terraform/aws/R81/gwlb-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/gwlb-master/main.tf create mode 100755 deprecated/terraform/aws/R81/gwlb-master/output.tf create mode 100755 deprecated/terraform/aws/R81/gwlb-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/gwlb-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/gwlb-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/gwlb/README.md create mode 100755 deprecated/terraform/aws/R81/gwlb/locals.tf create mode 100755 deprecated/terraform/aws/R81/gwlb/main.tf create mode 100755 deprecated/terraform/aws/R81/gwlb/output.tf create mode 100755 deprecated/terraform/aws/R81/gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R81/gwlb/versions.tf create mode 100755 deprecated/terraform/aws/R81/management/README.md create mode 100755 deprecated/terraform/aws/R81/management/locals.tf create mode 100755 deprecated/terraform/aws/R81/management/main.tf create mode 100755 deprecated/terraform/aws/R81/management/management_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/management/output.tf create mode 100755 deprecated/terraform/aws/R81/management/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/management/variables.tf create mode 100755 deprecated/terraform/aws/R81/management/versions.tf create mode 100755 deprecated/terraform/aws/R81/mds/README.md create mode 100755 deprecated/terraform/aws/R81/mds/locals.tf create mode 100755 deprecated/terraform/aws/R81/mds/main.tf create mode 100755 deprecated/terraform/aws/R81/mds/mds_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/mds/output.tf create mode 100755 deprecated/terraform/aws/R81/mds/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/mds/variables.tf create mode 100755 deprecated/terraform/aws/R81/mds/versions.tf create mode 100755 deprecated/terraform/aws/R81/modules/amis/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/amis/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/amis/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/cloudwatch-policy/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/cloudwatch-policy/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/cluster-iam-role/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/cluster-iam-role/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/elastic_ip/locals.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/elastic_ip/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/elastic_ip/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/elastic_ip/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/gateway_instance/gateway_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/modules/common/gateway_instance/locals.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/gateway_instance/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/gateway_instance/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/gateway_instance/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/instance_type/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/instance_type/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/internal_default_route/locals.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/internal_default_route/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/internal_default_route/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/internal_default_route/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/load_balancer/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/load_balancer/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/load_balancer/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/permissive_sg/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/permissive_sg/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/permissive_sg/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/version_license/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/common/version_license/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/custom-autoscale/locals.tf create mode 100755 deprecated/terraform/aws/R81/modules/custom-autoscale/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/custom-autoscale/variables.tf create mode 100755 deprecated/terraform/aws/R81/modules/vpc/main.tf create mode 100755 deprecated/terraform/aws/R81/modules/vpc/output.tf create mode 100755 deprecated/terraform/aws/R81/modules/vpc/variables.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale-master/README.md create mode 100755 deprecated/terraform/aws/R81/qs-autoscale-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale-master/main.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale-master/output.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/qs-autoscale-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale/README.md create mode 100755 deprecated/terraform/aws/R81/qs-autoscale/locals.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale/main.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale/output.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/qs-autoscale/variables.tf create mode 100755 deprecated/terraform/aws/R81/qs-autoscale/versions.tf create mode 100755 deprecated/terraform/aws/R81/standalone-master/README.md create mode 100755 deprecated/terraform/aws/R81/standalone-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/standalone-master/main.tf create mode 100755 deprecated/terraform/aws/R81/standalone-master/output.tf create mode 100755 deprecated/terraform/aws/R81/standalone-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/standalone-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/standalone-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/standalone/README.md create mode 100755 deprecated/terraform/aws/R81/standalone/locals.tf create mode 100755 deprecated/terraform/aws/R81/standalone/main.tf create mode 100755 deprecated/terraform/aws/R81/standalone/output.tf create mode 100755 deprecated/terraform/aws/R81/standalone/standalone_userdata.yaml create mode 100755 deprecated/terraform/aws/R81/standalone/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/standalone/variables.tf create mode 100755 deprecated/terraform/aws/R81/standalone/versions.tf create mode 100755 deprecated/terraform/aws/R81/tests/cluster_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/cross_az_cluster_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/gateway_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/globals.go create mode 100755 deprecated/terraform/aws/R81/tests/gwlb_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/qs_autoscale_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/standalone_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/tgw_asg_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/tgw_cross_az_cluster_master_test.go create mode 100755 deprecated/terraform/aws/R81/tests/tgw_gwlb_master_test.go create mode 100755 deprecated/terraform/aws/R81/tgw-asg-master/README.md create mode 100755 deprecated/terraform/aws/R81/tgw-asg-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg-master/main.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg-master/output.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/tgw-asg-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg/README.md create mode 100755 deprecated/terraform/aws/R81/tgw-asg/locals.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg/main.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg/output.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/tgw-asg/variables.tf create mode 100755 deprecated/terraform/aws/R81/tgw-asg/versions.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/README.md create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/main.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/output.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster/README.md create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster/locals.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster/main.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster/output.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster/variables.tf create mode 100755 deprecated/terraform/aws/R81/tgw-cross-az-cluster/versions.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb-master/README.md create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb-master/locals.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb-master/main.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb-master/output.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb-master/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb-master/variables.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb-master/versions.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb/README.md create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb/locals.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb/main.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb/output.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb/terraform.tfvars create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb/variables.tf create mode 100755 deprecated/terraform/aws/R81/tgw-gwlb/versions.tf diff --git a/.gitignore b/.gitignore index b19ec88e..61049654 100755 --- a/.gitignore +++ b/.gitignore @@ -137,4 +137,7 @@ dmypy.json .pytype/ # Cython debug symbols -cython_debug/ \ No newline at end of file +cython_debug/ + +# deprecated files +deprecated/ \ No newline at end of file diff --git a/aws/templates/cluster/README.md b/aws/templates/cluster/README.md index 03bbe934..4ffc3c43 100644 --- a/aws/templates/cluster/README.md +++ b/aws/templates/cluster/README.md @@ -23,4 +23,18 @@
-
\ No newline at end of file +
+## Revision History +In order to check the template version, please refer to [sk125252](https://support.checkpoint.com/results/sk/sk125252#ToggleR8120gateway) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------------------------------| +| 20240704 | - R80.40 version deprecation.
- R81 version deprecation. | +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20230923 | Add support for C5d instance type. | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Template version 20230503 and above supports Smart-1 Cloud token validation. | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud. | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Terraform module for AWS | diff --git a/aws/templates/geo-cluster/README.md b/aws/templates/geo-cluster/README.md index e6e30d5d..15f20e38 100644 --- a/aws/templates/geo-cluster/README.md +++ b/aws/templates/geo-cluster/README.md @@ -23,4 +23,18 @@
-
\ No newline at end of file +
+## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------------------------------| +| 20240704 | - R80.40 version deprecation.
- R81 version deprecation | +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20230923 | Add support for C5d instance type. | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Template version 20230503 and above supports Smart-1 Cloud token validation. | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud. | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Terraform module for AWS | diff --git a/aws/templates/gwlb-asg/README.md b/aws/templates/gwlb-asg/README.md index 26eda643..2eab3fa0 100644 --- a/aws/templates/gwlb-asg/README.md +++ b/aws/templates/gwlb-asg/README.md @@ -56,3 +56,18 @@

+ +## Revision History +In order to check the template version, please refer to [sk125252](https://support.checkpoint.com/results/sk/sk125252#ToggleR8120gateway) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | - R80.40 version deprecation.
- R81 version deprecation | +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240414 | Add support for Elastic Load Balancer Health Checks. | +| 20230923 | Add support for C5d instance type. | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221226 | Support ASG Launch Template instead of Launch Configuration. | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point Auto Scaling GWLB Terraform module for AWS | diff --git a/aws/templates/management/README.md b/aws/templates/management/README.md index f8565c48..8b1950f0 100644 --- a/aws/templates/management/README.md +++ b/aws/templates/management/README.md @@ -19,4 +19,17 @@
-
\ No newline at end of file +
+## Revision History +In order to check the template version, please refer to [sk125252](https://support.checkpoint.com/results/sk/sk125252#ToggleR8120gateway) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | - R80.40 version deprecation.
- R81 version deprecation. | +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20230923 | Add support for C5d instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Security Management Server Terraform module for AWS | diff --git a/aws/templates/single-gw/README.md b/aws/templates/single-gw/README.md index 34e01aba..81e7b828 100644 --- a/aws/templates/single-gw/README.md +++ b/aws/templates/single-gw/README.md @@ -23,3 +23,18 @@

+ +## Revision History +In order to check the template version, please refer to [sk125252](https://support.checkpoint.com/results/sk/sk125252#ToggleR8120gateway) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | - R80.40 version deprecation.
- R81 version deprecation. | +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231113 | Stability fixes. | +| 20230923 | Add support for C5d instance type. | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Template version 20230503 and above supports Smart-1 Cloud token validation. | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support. | diff --git a/aws/templates/standalone/README.md b/aws/templates/standalone/README.md index b7afb4c3..2cc7031d 100644 --- a/aws/templates/standalone/README.md +++ b/aws/templates/standalone/README.md @@ -24,3 +24,18 @@

+ +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------| +| 20240704 | - R80.40 version deprecation.
- R81 version deprecation. | +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231113 | - Stability fixes.
- Add support for BYOL license type for Standalone. | +| 20230923 | Add support for C5d instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Terraform module for AWS | diff --git a/aws/templates/tgw-asg/README.md b/aws/templates/tgw-asg/README.md index 1ea088d6..668bebf8 100644 --- a/aws/templates/tgw-asg/README.md +++ b/aws/templates/tgw-asg/README.md @@ -24,3 +24,17 @@

+ +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------| +| 20240704 | - R80.40 version deprecation.
- R81 version deprecation. | +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240414 | Add support for Elastic Load Balancer Health Checks. | +| 20230923 | Add support for C5d instance type. | +| 20221226 | Support ASG Launch Template instead of Launch Configuration. | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support. | +| 20210329 | First release of Check Point Transit Gateway Auto Scaling Group Terraform module for AWS | diff --git a/aws/templates/tgw-cross-az-cluster/README.md b/aws/templates/tgw-cross-az-cluster/README.md index f1a6b492..e4c4eec2 100644 --- a/aws/templates/tgw-cross-az-cluster/README.md +++ b/aws/templates/tgw-cross-az-cluster/README.md @@ -23,4 +23,16 @@
-
\ No newline at end of file +
+## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20230923 | Add support for C5d instance type. | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation. | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud.
- Multiple VIPs support for Cross Availability Zone Cluster. | +| 20221229 | Removed unsupported versions. | +| 20221123 | Templates version 20221120 and above support R81.20 | diff --git a/aws/templates/tgw-ha/README.md b/aws/templates/tgw-ha/README.md index f069cdd5..a2754f4a 100644 --- a/aws/templates/tgw-ha/README.md +++ b/aws/templates/tgw-ha/README.md @@ -23,4 +23,17 @@
-
\ No newline at end of file +
+## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------------------------------| +| 20240519 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20230923 | Add support for C5d instance type. | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Template version 20230503 and above supports Smart-1 Cloud token validation. | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud. | +| 20221123 | Templates version 20221120 and above support R81.20 | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Terraform module for AWS | diff --git a/deprecated/aws/templates/gateway-r7730/README.md b/deprecated/aws/templates/R77.30/gateway-r7730/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/gateway-r7730/README.md rename to deprecated/aws/templates/R77.30/gateway-r7730/README.md diff --git a/deprecated/aws/templates/gateway-r7730/gateway-2-nic-existing-vpc.json b/deprecated/aws/templates/R77.30/gateway-r7730/gateway-2-nic-existing-vpc.json similarity index 100% rename from deprecated/aws/templates/gateway-r7730/gateway-2-nic-existing-vpc.json rename to deprecated/aws/templates/R77.30/gateway-r7730/gateway-2-nic-existing-vpc.json diff --git a/deprecated/aws/templates/gateways-r7730/README.md b/deprecated/aws/templates/R77.30/gateways-r7730/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/gateways-r7730/README.md rename to deprecated/aws/templates/R77.30/gateways-r7730/README.md diff --git a/deprecated/aws/templates/gateways-r7730/inter-az-cluster.json b/deprecated/aws/templates/R77.30/gateways-r7730/inter-az-cluster.json similarity index 100% rename from deprecated/aws/templates/gateways-r7730/inter-az-cluster.json rename to deprecated/aws/templates/R77.30/gateways-r7730/inter-az-cluster.json diff --git a/deprecated/aws/templates/instance-r7730/README.md b/deprecated/aws/templates/R77.30/instance-r7730/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/instance-r7730/README.md rename to deprecated/aws/templates/R77.30/instance-r7730/README.md diff --git a/deprecated/aws/templates/instance-r7730/gwinvpc.json b/deprecated/aws/templates/R77.30/instance-r7730/gwinvpc.json similarity index 100% rename from deprecated/aws/templates/instance-r7730/gwinvpc.json rename to deprecated/aws/templates/R77.30/instance-r7730/gwinvpc.json diff --git a/deprecated/aws/templates/management-r7730/README.md b/deprecated/aws/templates/R77.30/management-r7730/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/management-r7730/README.md rename to deprecated/aws/templates/R77.30/management-r7730/README.md diff --git a/deprecated/aws/templates/management-r7730/r7730-management.json b/deprecated/aws/templates/R77.30/management-r7730/r7730-management.json similarity index 100% rename from deprecated/aws/templates/management-r7730/r7730-management.json rename to deprecated/aws/templates/R77.30/management-r7730/r7730-management.json diff --git a/deprecated/aws/templates/asg-r8030/README.md b/deprecated/aws/templates/R80.30/asg-r8030/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/asg-r8030/README.md rename to deprecated/aws/templates/R80.30/asg-r8030/README.md diff --git a/deprecated/aws/templates/asg-r8030/autoscale.json b/deprecated/aws/templates/R80.30/asg-r8030/autoscale.json similarity index 100% rename from deprecated/aws/templates/asg-r8030/autoscale.json rename to deprecated/aws/templates/R80.30/asg-r8030/autoscale.json diff --git a/deprecated/aws/templates/cluster-r8030/README.md b/deprecated/aws/templates/R80.30/cluster-r8030/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/cluster-r8030/README.md rename to deprecated/aws/templates/R80.30/cluster-r8030/README.md diff --git a/deprecated/aws/templates/cluster-r8030/cluster-into-vpc.json b/deprecated/aws/templates/R80.30/cluster-r8030/cluster-into-vpc.json old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/cluster-r8030/cluster-into-vpc.json rename to deprecated/aws/templates/R80.30/cluster-r8030/cluster-into-vpc.json diff --git a/deprecated/aws/templates/cluster-r8030/cluster.json b/deprecated/aws/templates/R80.30/cluster-r8030/cluster.json old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/cluster-r8030/cluster.json rename to deprecated/aws/templates/R80.30/cluster-r8030/cluster.json diff --git a/deprecated/aws/templates/management-r8030/README.md b/deprecated/aws/templates/R80.30/management-r8030/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/management-r8030/README.md rename to deprecated/aws/templates/R80.30/management-r8030/README.md diff --git a/deprecated/aws/templates/management-r8030/management.json b/deprecated/aws/templates/R80.30/management-r8030/management.json similarity index 100% rename from deprecated/aws/templates/management-r8030/management.json rename to deprecated/aws/templates/R80.30/management-r8030/management.json diff --git a/deprecated/aws/templates/mds-r8030/README.md b/deprecated/aws/templates/R80.30/mds-r8030/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/mds-r8030/README.md rename to deprecated/aws/templates/R80.30/mds-r8030/README.md diff --git a/deprecated/aws/templates/mds-r8030/mds.json b/deprecated/aws/templates/R80.30/mds-r8030/mds.json similarity index 100% rename from deprecated/aws/templates/mds-r8030/mds.json rename to deprecated/aws/templates/R80.30/mds-r8030/mds.json diff --git a/deprecated/aws/templates/single-gw-r8030/README.md b/deprecated/aws/templates/R80.30/single-gw-r8030/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/single-gw-r8030/README.md rename to deprecated/aws/templates/R80.30/single-gw-r8030/README.md diff --git a/deprecated/aws/templates/single-gw-r8030/gateway-into-vpc.json b/deprecated/aws/templates/R80.30/single-gw-r8030/gateway-into-vpc.json old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/single-gw-r8030/gateway-into-vpc.json rename to deprecated/aws/templates/R80.30/single-gw-r8030/gateway-into-vpc.json diff --git a/deprecated/aws/templates/single-gw-r8030/gateway.json b/deprecated/aws/templates/R80.30/single-gw-r8030/gateway.json old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/single-gw-r8030/gateway.json rename to deprecated/aws/templates/R80.30/single-gw-r8030/gateway.json diff --git a/deprecated/aws/templates/tgw-asg-r8030/README.md b/deprecated/aws/templates/R80.30/tgw-asg-r8030/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/tgw-asg-r8030/README.md rename to deprecated/aws/templates/R80.30/tgw-asg-r8030/README.md diff --git a/deprecated/aws/templates/tgw-asg-r8030/checkpoint-tgw-asg-master.yaml b/deprecated/aws/templates/R80.30/tgw-asg-r8030/checkpoint-tgw-asg-master.yaml similarity index 100% rename from deprecated/aws/templates/tgw-asg-r8030/checkpoint-tgw-asg-master.yaml rename to deprecated/aws/templates/R80.30/tgw-asg-r8030/checkpoint-tgw-asg-master.yaml diff --git a/deprecated/aws/templates/tgw-asg-r8030/checkpoint-tgw-asg.yaml b/deprecated/aws/templates/R80.30/tgw-asg-r8030/checkpoint-tgw-asg.yaml similarity index 100% rename from deprecated/aws/templates/tgw-asg-r8030/checkpoint-tgw-asg.yaml rename to deprecated/aws/templates/R80.30/tgw-asg-r8030/checkpoint-tgw-asg.yaml diff --git a/deprecated/aws/templates/transit-vpc-r8030/README.md b/deprecated/aws/templates/R80.30/transit-vpc-r8030/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/transit-vpc-r8030/README.md rename to deprecated/aws/templates/R80.30/transit-vpc-r8030/README.md diff --git a/deprecated/aws/templates/transit-vpc-r8030/checkpoint-transit-master.yaml b/deprecated/aws/templates/R80.30/transit-vpc-r8030/checkpoint-transit-master.yaml similarity index 100% rename from deprecated/aws/templates/transit-vpc-r8030/checkpoint-transit-master.yaml rename to deprecated/aws/templates/R80.30/transit-vpc-r8030/checkpoint-transit-master.yaml diff --git a/deprecated/aws/templates/transit-vpc-r8030/checkpoint-transit.yaml b/deprecated/aws/templates/R80.30/transit-vpc-r8030/checkpoint-transit.yaml similarity index 100% rename from deprecated/aws/templates/transit-vpc-r8030/checkpoint-transit.yaml rename to deprecated/aws/templates/R80.30/transit-vpc-r8030/checkpoint-transit.yaml diff --git a/deprecated/aws/templates/transit-vpc-r8030/transit-master.yaml b/deprecated/aws/templates/R80.30/transit-vpc-r8030/transit-master.yaml similarity index 100% rename from deprecated/aws/templates/transit-vpc-r8030/transit-master.yaml rename to deprecated/aws/templates/R80.30/transit-vpc-r8030/transit-master.yaml diff --git a/deprecated/aws/templates/transit-vpc-r8030/transit.yaml b/deprecated/aws/templates/R80.30/transit-vpc-r8030/transit.yaml similarity index 100% rename from deprecated/aws/templates/transit-vpc-r8030/transit.yaml rename to deprecated/aws/templates/R80.30/transit-vpc-r8030/transit.yaml diff --git a/deprecated/aws/templates/R80.40/autoscale/autoscale.yaml b/deprecated/aws/templates/R80.40/autoscale/autoscale.yaml new file mode 100755 index 00000000..ce35a882 --- /dev/null +++ b/deprecated/aws/templates/R80.40/autoscale/autoscale.yaml @@ -0,0 +1,612 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Create an Auto Scaling group of Check Point gateways (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - GatewaysSubnets + - Label: + default: EC2 Instances Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - VolumeSize + - VolumeType + - EnableVolumeEncryption + - EnableInstanceConnect + - MetaDataToken + - Label: + default: Auto Scaling Configuration + Parameters: + - GatewaysMinSize + - GatewaysMaxSize + - AdminEmail + - GatewaysTargetGroups + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - Label: + default: Automatic Provisioning with Security Management Server Settings + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + - Label: + default: Proxy Configuration (optional) + Parameters: + - ELBType + - ELBPort + - ELBClients + ParameterLabels: + VPC: + default: VPC + GatewaysSubnets: + default: Gateways subnets + GatewayName: + default: Gateways name + GatewayInstanceType: + default: Gateways instance type + KeyName: + default: Key name + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableVolumeEncryption: + default: Enable volume encryption + EnableInstanceConnect: + default: Enable AWS Instance Connect + MetaDataToken: + default: Metadata HTTP token + GatewaysMinSize: + default: Minimum Gateway group size + GatewaysMaxSize: + default: Maximum Gateway group size + AdminEmail: + default: Email address + GatewaysTargetGroups: + default: Gateways target groups + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Gateways bootstrap script + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + ELBType: + default: Proxy type + ELBPort: + default: Proxy port + ELBClients: + default: Allowed proxy clients +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + GatewaysSubnets: + Description: Select at least 2 public subnets in the VPC. + Type: List + MinLength: 2 + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The instance type of the Secutiry Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableVolumeEncryption: + Description: Encrypt Auto Scaling instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewaysMinSize: + Description: The minimal number of gateways in the Auto Scaling group. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of gateways in the Auto Scaling group. + Type: Number + Default: 10 + MinValue: 1 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + ConstraintDescription: Must be a valid email address. + GatewaysTargetGroups: + Description: A list of Target Groups to associate with the Auto Scaling. + group (comma separated list of ARNs, without spaces) (optional) + Type: String + Default: '' + GatewayVersion: + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD". + to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections. + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: ASG-configuration + MinLength: 1 + MaxLength: 30 + ELBType: + Type: String + Default: none + AllowedValues: + - none + - internal + - internet-facing + ELBPort: + Type: Number + Default: 8080 + ELBClients: + Type: String + Default: 0.0.0.0/0 + AllowedPattern: '^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})/(\d{1,2})$' +Conditions: + ProvidedAdminEmail: !Not [!Equals [!Ref AdminEmail, '']] + ProvidedTargetGroups: !Not [!Equals [!Ref GatewaysTargetGroups, '']] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + CreateELB: !Not [!Equals [!Ref ELBType, none]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ChkpGatewayRole: + Type: AWS::IAM::Role + Condition: EnableCloudWatch + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: + - ec2.amazonaws.com + Action: + - sts:AssumeRole + Path: / + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: ChkpGatewayPolicy + PolicyRole: !Ref ChkpGatewayRole + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: EnableCloudWatch + Properties: + Path: / + Roles: + - !Ref ChkpGatewayRole + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion, GW]] + NotificationTopic: + Type: AWS::SNS::Topic + Condition: ProvidedAdminEmail + Properties: + Subscription: + - Endpoint: !Ref AdminEmail + Protocol: email + ElasticLoadBalancer: + Type: AWS::ElasticLoadBalancing::LoadBalancer + Condition: CreateELB + Properties: + CrossZone: true + Listeners: + - LoadBalancerPort: !Ref ELBPort + InstancePort: !Ref ELBPort + Protocol: TCP + HealthCheck: + Target: !Join [':', [TCP, !Ref ELBPort]] + HealthyThreshold: 3 + UnhealthyThreshold: 5 + Interval: 30 + Timeout: 5 + Scheme: !Ref ELBType + Subnets: !Ref GatewaysSubnets + Policies: + - PolicyName: EnableProxyProtocol + PolicyType: ProxyProtocolPolicyType + Attributes: + - Name: ProxyProtocol + Value: true + InstancePorts: + - !Ref ELBPort + SecurityGroups: + - !Ref ELBSecurityGroup + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + Tags: + - Key: Name + Value: !Join ['_', [!Ref 'AWS::StackName', PermissiveSecurityGroup]] + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + GatewayGroup: + Type: AWS::AutoScaling::AutoScalingGroup + DependsOn: GatewayLaunchTemplate + Properties: + VPCZoneIdentifier: !Ref GatewaysSubnets + LaunchTemplate: + LaunchTemplateId: !Ref GatewayLaunchTemplate + Version: !GetAtt GatewayLaunchTemplate.LatestVersionNumber + MinSize: !Ref GatewaysMinSize + MaxSize: !Ref GatewaysMaxSize + LoadBalancerNames: !If [CreateELB, [!Ref ElasticLoadBalancer], !Ref 'AWS::NoValue'] + TargetGroupARNs: !If [ProvidedTargetGroups, !Split [',', !Ref GatewaysTargetGroups], !Ref 'AWS::NoValue'] + HealthCheckType: ELB + HealthCheckGracePeriod: 3600 + NotificationConfiguration: !If + - ProvidedAdminEmail + - TopicARN: !Ref NotificationTopic + NotificationTypes: + - autoscaling:EC2_INSTANCE_LAUNCH + - autoscaling:EC2_INSTANCE_LAUNCH_ERROR + - autoscaling:EC2_INSTANCE_TERMINATE + - autoscaling:EC2_INSTANCE_TERMINATE_ERROR + - !Ref 'AWS::NoValue' + Tags: + - Key: Name + Value: !Ref GatewayName + PropagateAtLaunch: true + - Key: x-chkp-tags + Value: !Join + - ':' + - - !Join ['=', [management, !Ref ManagementServer]] + - !Join ['=', [template, !Ref ConfigurationTemplate]] + - !Join ['=', [ip-address, !Ref ControlGatewayOverPrivateOrPublicAddress]] + PropagateAtLaunch: true + GatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: true + Groups: + - !Ref PermissiveSecurityGroup + Monitoring: + Enabled: true + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [EnableCloudWatch, !Ref InstanceProfile, !Ref 'AWS::NoValue'] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect}' + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" sicKey=\"${sic}\" installationType=\"autoscale\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"autoscale\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + GatewayScaleUpPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref GatewayGroup + Cooldown: 300 + ScalingAdjustment: 1 + GatewayScaleDownPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref GatewayGroup + Cooldown: 300 + ScalingAdjustment: -1 + CPUAlarmHigh: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-up if CPU > 80% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 80 + AlarmActions: + - !Ref GatewayScaleUpPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref GatewayGroup + ComparisonOperator: GreaterThanThreshold + CPUAlarmLow: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-down if CPU < 60% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 60 + AlarmActions: + - !Ref GatewayScaleDownPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref GatewayGroup + ComparisonOperator: LessThanThreshold + ELBSecurityGroup: + Type: AWS::EC2::SecurityGroup + Condition: CreateELB + Properties: + GroupDescription: ELB security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: tcp + CidrIp: !Ref ELBClients + FromPort: !Ref ELBPort + ToPort: !Ref ELBPort +Outputs: + URL: + Description: The URL of the Proxy. + Condition: CreateELB + Value: !Join ['', ['http://', !GetAtt ElasticLoadBalancer.DNSName]] + SecurityGroup: + Description: The Security Group of the Auto Scaling group. + Value: !GetAtt PermissiveSecurityGroup.GroupId + diff --git a/deprecated/aws/templates/R80.40/autoscale/custom-autoscale.yaml b/deprecated/aws/templates/R80.40/autoscale/custom-autoscale.yaml new file mode 100755 index 00000000..70782d13 --- /dev/null +++ b/deprecated/aws/templates/R80.40/autoscale/custom-autoscale.yaml @@ -0,0 +1,226 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Create an Auto Scaling group of workload servers (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - ServersSubnets + - Label: + default: EC2 Instances Configuration + Parameters: + - ServerAMI + - ServerName + - ServerInstanceType + - KeyName + - AllocatePublicAddress + - Label: + default: Auto Scaling Configuration + Parameters: + - ServersMinSize + - ServersMaxSize + - AdminEmail + - ServersTargetGroups + - SourceSecurityGroup + ParameterLabels: + VPC: + default: VPC + ServersSubnets: + default: Servers subnets + ServerAMI: + default: Amazon Image ID + ServerName: + default: Instance Name + ServerInstanceType: + default: Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + ServersMinSize: + default: Minimum group size + ServerMaxSize: + default: Maximum group size + AdminEmail: + default: Email address + ServersTargetGroups: + default: Target Groups + SourceSecurityGroup: + default: Source Security Group +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ServersSubnets: + Description: Select at least 2 subnets in the VPC. + Type: List + MinLength: 2 + ServerAMI: + Description: AMI of the servers. + Type: String + AllowedPattern: '^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$' + ConstraintDescription: Must be a valid Amazon Machine Image ID. + ServerName: + Description: The servers name tag. + Type: String + Default: Server + ServerInstanceType: + Description: The instance type of the servers. + Type: String + Default: t3.micro + AllowedValues: + - t3.nano + - t3.micro + - t3.small + - t3.medium + - t3.large + - t3.xlarge + - t3.2xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an elastic IP for each server. + Type: String + Default: false + AllowedValues: + - true + - false + ServersMinSize: + Description: The minimal number of servers in the Auto Scaling group. + Type: Number + Default: 2 + MinValue: 1 + ServersMaxSize: + Description: The maximal number of servers in the Auto Scaling group. + Type: Number + Default: 10 + MinValue: 1 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. + (optional) + Type: String + Default: '' + AllowedPattern: '(|([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))' + ConstraintDescription: Must be a valid email address. + ServersTargetGroups: + Description: An optional list of Target Groups to associate with the Auto Scaling group (comma separated list of ARNs, without spaces). + Type: String + Default: '' + SourceSecurityGroup: + Description: The ID of Security Group from which access will be allowed to the instances in this Auto Scaling group. + Type: String + Default: '' +Conditions: + ProvidedAdminEmail: !Not [!Equals [!Ref AdminEmail, '']] + ProvidedTargetGroups: !Not [!Equals [!Ref ServersTargetGroups, '']] + NotProvidedSecurityGroup: !Equals [!Ref SourceSecurityGroup, ''] +Resources: + NotificationTopic: + Type: AWS::SNS::Topic + Condition: ProvidedAdminEmail + Properties: + Subscription: + - Endpoint: !Ref AdminEmail + Protocol: email + ServersSecurityGroup: + Type: AWS::EC2::SecurityGroup + Condition: NotProvidedSecurityGroup + Properties: + Tags: + - Key: Name + Value: !Join ['_', [!Ref 'AWS::StackName', ServersSecurityGroup]] + GroupDescription: Servers security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + ServersLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: !Ref AllocatePublicAddress + Groups: !If [NotProvidedSecurityGroup, [!Ref ServersSecurityGroup], [!Ref SourceSecurityGroup]] + Monitoring: + Enabled: true + KeyName: !Ref KeyName + ImageId: !Ref ServerAMI + InstanceType: !Ref ServerInstanceType + VersionDescription: Initial template version + ServersGroup: + Type: AWS::AutoScaling::AutoScalingGroup + Properties: + VPCZoneIdentifier: !Ref ServersSubnets + LaunchTemplate: + LaunchTemplateId: !Ref ServersLaunchTemplate + Version: !GetAtt ServersLaunchTemplate.LatestVersionNumber + MinSize: !Ref ServersMinSize + MaxSize: !Ref ServersMaxSize + TargetGroupARNs: !If [ProvidedTargetGroups, !Split [',', !Ref ServersTargetGroups], !Ref 'AWS::NoValue'] + NotificationConfiguration: !If + - ProvidedAdminEmail + - TopicARN: !Ref NotificationTopic + NotificationTypes: + - autoscaling:EC2_INSTANCE_LAUNCH + - autoscaling:EC2_INSTANCE_LAUNCH_ERROR + - autoscaling:EC2_INSTANCE_TERMINATE + - autoscaling:EC2_INSTANCE_TERMINATE_ERROR + - !Ref 'AWS::NoValue' + Tags: + - Key: Name + Value: !Ref ServerName + PropagateAtLaunch: true + ScaleUpPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref ServersGroup + Cooldown: 300 + ScalingAdjustment: 1 + ScaleDownPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref ServersGroup + Cooldown: 300 + ScalingAdjustment: -1 + CPUAlarmHigh: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-up if CPU > 80% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 80 + AlarmActions: + - !Ref ScaleUpPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref ServersGroup + ComparisonOperator: GreaterThanThreshold + CPUAlarmLow: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-down if CPU < 60% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 60 + AlarmActions: + - !Ref ScaleDownPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref ServersGroup + ComparisonOperator: LessThanThreshold diff --git a/deprecated/aws/templates/R80.40/autoscale/tgw-asg-master.yaml b/deprecated/aws/templates/R80.40/autoscale/tgw-asg-master.yaml new file mode 100755 index 00000000..e2ba00b4 --- /dev/null +++ b/deprecated/aws/templates/R80.40/autoscale/tgw-asg-master.yaml @@ -0,0 +1,684 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Network Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - CloudWatch + - ASN + - AdminEmail + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - ManagementPermissions + - ManagementPredefinedRole + - GatewaysBlades + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + - Label: + default: Automatic Provisioning with Security Management Server Settings + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public Subnet 1 + PublicSubnet2CIDR: + default: Public Subnet 2 + PublicSubnet3CIDR: + default: Public Subnet 3 + PublicSubnet4CIDR: + default: Public Subnet 4 + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + GatewayName: + default: GatewayName + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + CloudWatch: + default: CloudWatch metrics + ASN: + default: BGP ASN + AdminEmail: + default: Email address + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Instance type + ManagementVersion: + default: Version & license + ManagementPasswordHash: + default: Password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + ManagementPermissions: + default: IAM role + ManagementPredefinedRole: + default: Existing IAM role name + GatewaysBlades: + default: Default Blades + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + AvailabilityZones: + Description: List of Availability Zones (AZs) to use for the subnets in the VPC. Select at least two. + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + VPCCIDR: + Description: CIDR block for the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. If you choose to deploy a Security Management Server it will be deployed in this subnet. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet3CIDR: + Description: CIDR block for public subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet4CIDR: + Description: CIDR block for public subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + ASN: + Description: The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways. + Type: String + AllowedPattern: '^[0-9]+$' + Default: 65000 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + ConstraintDescription: Must be a valid email address. + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The version and license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read-write permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + ManagementPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'. + Type: String + Default: '' + GatewaysBlades: + Description: Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (these and additional Blades can be manually turned on or off later). + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^$|^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: TGW-ASG-configuration + MinLength: 1 + MaxLength: 30 +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PublicSubnet3CIDR: !Ref PublicSubnet3CIDR + PublicSubnet4CIDR: !Ref PublicSubnet4CIDR + CreatePrivateSubnets: false + MainStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/autoscale/tgw-asg.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + GatewaysSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.PublicSubnet1ID + - !GetAtt VPCStack.Outputs.PublicSubnet2ID + - !If [3AZs, !GetAtt VPCStack.Outputs.PublicSubnet3ID, !Ref 'AWS::NoValue'] + - !If [4AZs, !GetAtt VPCStack.Outputs.PublicSubnet4ID, !Ref 'AWS::NoValue'] + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + AllowUploadDownload: !Ref AllowUploadDownload + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + CloudWatch: !Ref CloudWatch + ASN: !Ref ASN + AdminEmail: !Ref AdminEmail + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + ManagementPermissions: !Ref ManagementPermissions + ManagementPredefinedRole: !Ref ManagementPredefinedRole + GatewaysBlades: !Ref GatewaysBlades + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate +Outputs: + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !Ref ConfigurationTemplate + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name. + Value: !GetAtt MainStack.Outputs.ControllerName + ManagementPublicAddress: + Description: The public address of the management servers. + Value: !GetAtt MainStack.Outputs.ManagementPublicAddress + Condition: DeployManagement +Rules: + GatewayAddressRule: + RuleCondition: !Equals [!Ref ManagementDeploy, 'true'] + Assertions: + - AssertDescription: "Gateway's netowrk to communicate with the Security Management Server must be provided" + Assert: !Not [ !Equals [!Ref GatewaysAddresses, '']] \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/autoscale/tgw-asg.yaml b/deprecated/aws/templates/R80.40/autoscale/tgw-asg.yaml new file mode 100755 index 00000000..1214a989 --- /dev/null +++ b/deprecated/aws/templates/R80.40/autoscale/tgw-asg.yaml @@ -0,0 +1,676 @@ +AWSTemplateFormatVersion: '2010-09-09' +Description: Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Network Configuration + Parameters: + - VPC + - GatewaysSubnets + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - CloudWatch + - ASN + - AdminEmail + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - ManagementPermissions + - ManagementPredefinedRole + - GatewaysBlades + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + - Label: + default: Automatic Provisioning with Security Management Server Settings + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + VPC: + default: VPC + GatewaysSubnets: + default: Subnets + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + GatewayName: + default: Name + GatewayInstanceType: + default: Instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Version & license + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + CloudWatch: + default: CloudWatch metrics + ASN: + default: BGP ASN + AdminEmail: + default: Email address + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Instance type + ManagementVersion: + default: Version & license + ManagementPasswordHash: + default: Password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + ManagementPermissions: + default: IAM role + ManagementPredefinedRole: + default: Existing IAM role name + GatewaysBlades: + default: Default Blades + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses + GatewayManagement: + default: Manage Gateways + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: You must select a VPC. + GatewaysSubnets: + Description: Select at least 2 external subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet. + Type: List + MinLength: 2 + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + ASN: + Description: The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways. + Type: String + Default: 65000 + AllowedPattern: '^[0-9]+$' + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + ConstraintDescription: Must be a valid email address. + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The version and license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read-write permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + ManagementPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'. + Type: String + Default: '' + GatewaysBlades: + Description: Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (these and additional Blades can be manually turned on or off later). + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^$|^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: TGW-ASG-configuration + MinLength: 1 + MaxLength: 30 +Conditions: + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] + DeployManagement: !Equals [!Ref ManagementDeploy, true] +Resources: + ManagementStack: + Type: AWS::CloudFormation::Stack + Condition: DeployManagement + Properties: + TemplateURL: __URL__/management/management.yaml + Parameters: + VPC: !Ref VPC + ManagementSubnet: !Select [0, !Ref GatewaysSubnets] + ManagementName: !Ref ManagementServer + ManagementInstanceType: !Ref ManagementInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: true + VolumeEncryption: !If [VolumeEncryption, alias/aws/ebs, ''] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + ManagementPermissions: !Ref ManagementPermissions + ManagementPredefinedRole: !Ref ManagementPredefinedRole + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + AllowUploadDownload: !Ref AllowUploadDownload + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + ManagementBootstrapScript: !Join + - ';' + - - 'echo -e "\nStarting Bootstrap script\n"' + - 'echo "Setting up bootstrap parameters"' + - !Sub 'conf_template=${ConfigurationTemplate} ; mgmt=${ManagementServer} ; region=${AWS::Region} ; blades=${GatewaysBlades}' + - !Sub ['version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - !Join ['', ['sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ' | base64 -d)"']] + - 'community="tgw-community" ; controller="tgw-controller"' + - 'echo "Adding tgw identifier to cloud-version"' + - 'template="management_tgw_asg"' + - 'cv_path="/etc/cloud-version"' + - 'if test -f ${cv_path}; then sed -i ''/template_name/c\template_name: ''"${template}"'''' /etc/cloud-version; fi' + - 'cv_json_path="/etc/cloud-version.json"' + - 'cv_json_path_tmp="/etc/cloud-version-tmp.json"' + - 'if test -f ${cv_json_path}; then cat ${cv_json_path} | jq ''.template_name = "''"${template}"''"'' > ${cv_json_path_tmp}; mv ${cv_json_path_tmp} ${cv_json_path}; fi' + - 'echo "Configuring VPN community: ${community}"' + - '[[ -d /opt/CPcme/menu/additions ]] && /opt/CPcme/menu/additions/config-community.sh "${community}" || /etc/fw/scripts/autoprovision/config-community.sh "${community}"' + - 'echo "Setting VPN rules"' + - 'mgmt_cli -r true add access-layer name "Inline"' + - 'mgmt_cli -r true add access-rule layer Network position 1 name "${community} VPN Traffic Rule" vpn.directional.1.from "${community}" vpn.directional.1.to "${community}" vpn.directional.2.from "${community}" vpn.directional.2.to External_clear action "Apply Layer" source "Any" destination "Any" service "Any" inline-layer "Inline"' + - 'mgmt_cli -r true add dynamic-object name "LocalGateway"' + - 'mgmt_cli -r true add nat-rule package standard position bottom install-on "Policy Targets" original-source All_Internet translated-source "LocalGateway" method hide' + - 'echo "Setting CME configurations"' + - 'autoprov_cfg -f init AWS -mn "${mgmt}" -tn "${conf_template}" -cn "${controller}" -po Standard -otp "${sic}" -r "${region}" -ver "${version}" -iam -dt TGW' + - 'autoprov_cfg -f set controller AWS -cn "${controller}" -sv -com "${community}"' + - 'autoprov_cfg -f set template -tn "${conf_template}" -vpn -vd "" -con "${community}"' + - '${blades} && autoprov_cfg -f set template -tn "${conf_template}" -ia -ips -appi -av -ab' + - 'echo -e "\nFinished Bootstrap script\n"' + SecurityGatewaysStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/autoscale/autoscale.yaml + Parameters: + VPC: !Ref VPC + GatewaysSubnets: !Join [',', !Ref GatewaysSubnets] + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + MetaDataToken: !Ref MetaDataToken + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + AdminEmail: !Ref AdminEmail + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Join + - ';' + - - 'echo -e "\nStarting Bootstrap script\n"' + - 'echo "Setting up bootstrap parameters"' + - !Sub 'asn=${ASN}' + - 'echo "Adding tgw identifier to cloud-version"' + - 'template="autoscale_tgw"' + - 'cv_path="/etc/cloud-version"' + - 'if test -f ${cv_path}; then sed -i ''/template_name/c\template_name: ''"${template}"'''' /etc/cloud-version; fi' + - 'cv_json_path="/etc/cloud-version.json"' + - 'cv_json_path_tmp="/etc/cloud-version-tmp.json"' + - 'if test -f ${cv_json_path}; then cat ${cv_json_path} | jq ''.template_name = "''"${template}"''"'' > ${cv_json_path_tmp}; mv ${cv_json_path_tmp} ${cv_json_path}; fi' + - 'echo "Setting ASN to: ${asn}"' + - 'clish -c "set as ${asn}" -s' + - 'echo -e "\nFinished Bootstrap script\n"' + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate +Outputs: + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !Ref ConfigurationTemplate + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name. + Value: tgw-controller + ManagementPublicAddress: + Description: The public address of the management servers. + Value: !GetAtt ManagementStack.Outputs.PublicAddress + Condition: DeployManagement +Rules: + GatewayAddressRule: + RuleCondition: !Equals [!Ref ManagementDeploy, 'true'] + Assertions: + - AssertDescription: "Gateway's netowrk to communicate with the Security Management Server must be provided" + Assert: !Not [ !Equals [!Ref GatewaysAddresses, '']] \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/cluster/cluster-master.yaml b/deprecated/aws/templates/R80.40/cluster/cluster-master.yaml new file mode 100755 index 00000000..37902602 --- /dev/null +++ b/deprecated/aws/templates/R80.40/cluster/cluster-master.yaml @@ -0,0 +1,512 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Check Point Cluster in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZone + - VPCCIDR + - PublicSubnetCIDR + - PrivateSubnetCIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPCCIDR: + default: VPC CIDR + AvailabilityZone: + default: Availability zone + PublicSubnetCIDR: + default: Public subnet CIDR + PrivateSubnetCIDR: + default: Private subnet CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + AvailabilityZone: + Description: The availability zone in which to deploy the cluster. + Type: AWS::EC2::AvailabilityZone::Name + MinLength: 1 + VPCCIDR: + Description: The CIDR block for your VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnetCIDR: + Description: The external subnet of the cluster. The cluster's public IPs will be generated from this subnet. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnetCIDR: + Description: The internal subnet of the cluster. The cluster's private IPs will be generated from this subnet. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Default: false + Type: String + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD". + to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections. + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources (optional). + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Ref AvailabilityZone + NumberOfAZs: 1 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnetCIDR + PrivateSubnet1CIDR: !Ref PrivateSubnetCIDR + InternalRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPCStack + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: Private Subnets Route Table + ClusterStack: + Type: AWS::CloudFormation::Stack + DependsOn: VPCStack + Properties: + TemplateURL: __URL__/cluster/cluster.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnet: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PrivateSubnet: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary +Outputs: + ClusterPublicAddress: + Description: The public address of the cluster. + Value: !GetAtt ClusterStack.Outputs.ClusterPublicAddress + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberAExternalInterface: + Condition: AllocateAddress + Description: The external interface of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAExternalInterface + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateExternalAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateInternalAddress + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateExternalAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateInternalAddress + ClusterPrivateAliasExternalAddress: + Description: The secondary external private IP address of the cluster. + Value: !GetAtt ClusterStack.Outputs.ClusterPrivateAliasExternalAddress + ClusterPrivateAliasInternalAddress: + Description: The secondary internal private IP address of the cluster. + Value: !GetAtt ClusterStack.Outputs.ClusterPrivateAliasInternalAddress +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/cluster/cluster.yaml b/deprecated/aws/templates/R80.40/cluster/cluster.yaml new file mode 100755 index 00000000..4b1c93e4 --- /dev/null +++ b/deprecated/aws/templates/R80.40/cluster/cluster.yaml @@ -0,0 +1,762 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Cluster into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnet + - PrivateSubnet + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnet: + default: Public subnet + PrivateSubnet: + default: Private subnet + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + PublicSubnet: + Description: The public subnet of the cluster. The cluster's public IPs will be generated from this subnet. The subnet's route table must have 0.0.0.0/0 route to Internet Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + PrivateSubnet: + Description: The private subnet of the cluster. The cluster's private IPs will be generated from this subnet. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + InternalRouteTable: + Description: The route table id in which to set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the route table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD". + to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections. + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources (optional). + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + CreateRole: !Equals [!Ref GatewayPredefinedRole, ''] + ProvidedPassHash: !Not [!Equals [!Ref GatewayPasswordHash, '']] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + EmptyHostName: !Equals [!Ref GatewayHostname, ''] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ClusterReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ClusterReadyCondition: + Type: AWS::CloudFormation::WaitCondition + DependsOn: [MemberAInstance, MemberBInstance] + Condition: AllocateAddress + Properties: + Count: 2 + Handle: !Ref ClusterReadyHandle + Timeout: 1800 + ClusterRole: + Condition: CreateRole + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cluster-iam-role.yaml + ClusterInstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [!If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole]] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + PolicyRole: !If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole] + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join [-, [!Ref GatewayVersion, GW]] + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + MemberAExternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member A external. + SecondaryPrivateIpAddressCount: 1 + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_ExternalInterface + MemberBExternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member B external. + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_ExternalInterface + MemberAInternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member A internal. + SecondaryPrivateIpAddressCount: 1 + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_InternalInterface + MemberBInternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member B internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_InternalInterface + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + DependsOn: MemberAInternalInterface + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref MemberAInternalInterface + RouteTableId: !Ref InternalRouteTable + PrivateSubnetRouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnet + MemberAInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberAExternalInterface, MemberAInternalInterface, MemberAGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberAGatewayLaunchTemplate + Version: !GetAtt MemberAGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-A]] + - Key: x-chkp-member-ips + Value: !Join + - ':' + - - !Join [ '=', [ public-ip, !If [ AllocateAddress, !Ref MemberAPublicAddress, '' ] ] ] + - !Join [ '=', [ external-private-ip, !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress ] ] + - !Join [ '=', [ internal-private-ip, !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress ] ] + - Key: x-chkp-cluster-ips + Value: !Join + - ':' + - - !Join [ '=', [ cluster-ip, !Ref ClusterPublicAddress ] ] + - !Join [ '=', [ cluster-eth0-private-ip, !Select [ 0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses ] ] ] + - !Join [ '=', [ cluster-eth1-private-ip, !Select [ 0, !GetAtt MemberAInternalInterface.SecondaryPrivateIpAddresses ] ] ] + MemberBInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberBExternalInterface, MemberBInternalInterface, MemberBGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberBGatewayLaunchTemplate + Version: !GetAtt MemberBGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-B]] + - Key: x-chkp-member-ips + Value: !Join + - ':' + - - !Join [ '=', [ public-ip, !If [ AllocateAddress, !Ref MemberBPublicAddress, '' ] ] ] + - !Join [ '=', [ external-private-ip, !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress ] ] + - !Join [ '=', [ internal-private-ip, !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress ] ] + - Key: x-chkp-cluster-ips + Value: !Join + - ':' + - - !Join [ '=', [ cluster-ip, !Ref ClusterPublicAddress ] ] + - !Join [ '=', [ cluster-eth0-private-ip, !Select [ 0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses ] ] ] + - !Join [ '=', [ cluster-eth1-private-ip, !Select [ 0, !GetAtt MemberAInternalInterface.SecondaryPrivateIpAddresses ] ] ] + MemberAGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberAExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberAInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenA=''${MemberAToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-a'] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberAPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenA}\"" installationType=\"cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + MemberBGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberBExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberBInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenB=''${MemberBToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-b'] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberBPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenB}\"" installationType=\"cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + ClusterPublicAddress: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + MemberAPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + MemberBPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + ClusterAddressAssoc: + Type: AWS::EC2::EIPAssociation + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt ClusterPublicAddress.AllocationId + PrivateIpAddress: !Select [0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses] + MemberAAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt MemberAPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberBAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberBInstance + Properties: + NetworkInterfaceId: !Ref MemberBExternalInterface + AllocationId: !GetAtt MemberBPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress +Outputs: + ClusterPublicAddress: + Description: The public address of the cluster. + Value: !Ref ClusterPublicAddress + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !Ref MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberAPublicAddress]] + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !Join ['', ['https://', !Ref MemberAPublicAddress]] + MemberAExternalInterface: + Condition: AllocateAddress + Description: The external interface of member A. + Value: !Ref MemberAExternalInterface + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !Ref MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberBPublicAddress]] + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !Join ['', ['https://', !Ref MemberBPublicAddress]] + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress + ClusterPrivateAliasExternalAddress: + Description: The secondary external private IP address of the cluster. + Value: !Select [ 0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses ] + ClusterPrivateAliasInternalAddress: + Description: The secondary internal private IP address of the cluster. + Value: !Select [ 0, !GetAtt MemberAInternalInterface.SecondaryPrivateIpAddresses ] + +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [[!Ref MemberBToken], !Ref MemberAToken] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] + + diff --git a/deprecated/aws/templates/R80.40/cluster/geo-cluster-master.yaml b/deprecated/aws/templates/R80.40/cluster/geo-cluster-master.yaml new file mode 100755 index 00000000..a135499c --- /dev/null +++ b/deprecated/aws/templates/R80.40/cluster/geo-cluster-master.yaml @@ -0,0 +1,523 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Check Point cross AZ Cluster in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PrivateSubnet1CIDR + - PrivateSubnet2CIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + AvailabilityZones: + default: Availability Zones + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PrivateSubnet1CIDR: + default: Private subnet 1 CIDR + PrivateSubnet2CIDR: + default: Private subnet 2 CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved). + Type: List + MinLength: 2 + VPCCIDR: + Description: CIDR block for the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. The cluster's public IPs will be generated from this subnet. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. The cluster's public IPs will be generated from this subnet. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet1CIDR: + Description: CIDR block for private subnet 1 located in the 1st Availability Zone. The cluster's private IPs will be generated from this subnet. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet2CIDR: + Description: CIDR block for private subnet 2 located in the 2nd Availability Zone. The cluster's private IPs will be generated from this subnet. + Type: String + Default: 10.0.21.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the Security Gateways. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: When choosing "false", make sure the cluster members can connect to an ec2 endpoint. + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Description: The license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to + get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between + Check Point components. Choose a random string consisting of at least 8 + alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: >- + Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: 2 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PrivateSubnet1CIDR: !Ref PrivateSubnet1CIDR + PrivateSubnet2CIDR: !Ref PrivateSubnet2CIDR + InternalRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPCStack + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: Private Subnets Route Table + ClusterStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/cluster/geo-cluster.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnetA: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PublicSubnetB: !GetAtt VPCStack.Outputs.PublicSubnet2ID + PrivateSubnetA: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + PrivateSubnetB: !GetAtt VPCStack.Outputs.PrivateSubnet2ID + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateExternalAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateInternalAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateExternalAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateInternalAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/cluster/geo-cluster.yaml b/deprecated/aws/templates/R80.40/cluster/geo-cluster.yaml new file mode 100755 index 00000000..9db1f13a --- /dev/null +++ b/deprecated/aws/templates/R80.40/cluster/geo-cluster.yaml @@ -0,0 +1,734 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point cross AZ Cluster into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnetA + - PublicSubnetB + - PrivateSubnetA + - PrivateSubnetB + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnetA: + default: Public subnet 1 + PublicSubnetB: + default: Public subnet 2 + PrivateSubnetA: + default: Private subnet 1 + PrivateSubnetB: + default: Private subnet 2 + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: you must select a VPC. + PublicSubnetA: + Description: Select a public subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the first Security Gateway. + PublicSubnetB: + Description: Select a public subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the second Security Gateway. + PrivateSubnetA: + Description: Select a private subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the first Security Gateway. + PrivateSubnetB: + Description: Select a private subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the second Security Gateway. + InternalRouteTable: + Description: Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the Route Table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the Security Gateways. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: When choosing "false", make sure the cluster members can connect to an ec2 endpoint. + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Description: The license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to + get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between + Check Point components. Choose a random string consisting of at least 8 + alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: >- + Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + CreateRole: !Equals [!Ref GatewayPredefinedRole, ''] + ProvidedPassHash: !Not [!Equals [!Ref GatewayPasswordHash, '']] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + EmptyHostName: !Equals [!Ref GatewayHostname, ''] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ClusterReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ClusterReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: AllocateAddress + DependsOn: [MemberAInstance, MemberBInstance] + Properties: + Count: 2 + Handle: !Ref ClusterReadyHandle + Timeout: 1800 + ClusterRole: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cluster-iam-role.yaml + ClusterInstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [!If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole]] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName' ] + PolicyRole: !If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole] + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion, GW]] + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + MemberAExternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: External. + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnetA + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_ExternalInterface + MemberBExternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: External. + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnetB + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_ExternalInterface + MemberAInternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: Internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnetA + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_InternalInterface + MemberBInternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: Internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnetB + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_InternalInterface + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + DependsOn: MemberAInternalInterface + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref MemberAInternalInterface + RouteTableId: !Ref InternalRouteTable + PrivateSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnetA + PrivateSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnetB + MemberAInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberAInternalInterface, MemberAGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberAGatewayLaunchTemplate + Version: !GetAtt MemberAGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-A]] + MemberBInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberBInternalInterface, MemberBGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberBGatewayLaunchTemplate + Version: !GetAtt MemberBGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-B]] + MemberAGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberAExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberAInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: !Base64 + 'Fn::Join': + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenA=''${MemberAToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-a'] + - !Join ['', [' other_member_ip="', !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress, '"']] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberAPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenA}\"" installationType=\"geo-cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"geo_cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" elasticIp=\"${eip}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" otherMemberIp=\"${other_member_ip}\" bootstrapScript64=\"${bootstrap}\"' + MemberBGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberBExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberBInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: !Base64 + 'Fn::Join': + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenB=''${MemberBToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-b'] + - !Join ['', [' other_member_ip="', !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress, '"']] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberBPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join [ '', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"' ] ] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenB}\"" installationType=\"geo-cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"geo_cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" otherMemberIp=\"${other_member_ip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + MemberAPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + MemberBPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + MemberAAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt MemberAPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberBAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberBInstance + Properties: + NetworkInterfaceId: !Ref MemberBExternalInterface + AllocationId: !GetAtt MemberBPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !Ref MemberAPublicAddress + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress + MemberAExternalInterface: + Description: The external interface of member A. + Value: !Ref MemberAExternalInterface + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberAPublicAddress]] + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !Join ['', ['https://', !Ref MemberAPublicAddress]] + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !Ref MemberBPublicAddress + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress + MemberBExternalInterface: + Description: The external interface of member B. + Value: !Ref MemberBExternalInterface + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberBPublicAddress]] + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !Join ['', ['https://', !Ref MemberBPublicAddress]] +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/cluster/tgw-ha-master.yaml b/deprecated/aws/templates/R80.40/cluster/tgw-ha-master.yaml new file mode 100755 index 00000000..b9321374 --- /dev/null +++ b/deprecated/aws/templates/R80.40/cluster/tgw-ha-master.yaml @@ -0,0 +1,531 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Check Point TGW HA cross AZ Cluster in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PrivateSubnet1CIDR + - PrivateSubnet2CIDR + - TgwSubnet1CIDR + - TgwSubnet2CIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + AvailabilityZones: + default: Availability Zones + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PrivateSubnet1CIDR: + default: Private subnet 1 CIDR + PrivateSubnet2CIDR: + default: Private subnet 2 CIDR + TgwSubnet1CIDR: + default: TGW HA subnet 1 CIDR + TgwSubnet2CIDR: + default: TGW HA subnet 2 CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved). + Type: List + MinLength: 2 + VPCCIDR: + Description: The CIDR block of the provided VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet1CIDR: + Description: CIDR block for private subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet2CIDR: + Description: CIDR block for private subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.21.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet1CIDR: + Description: CIDR block for TGW HA subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.12.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet2CIDR: + Description: CIDR block for TGW HA subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.22.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Default: false + Type: String + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: 2 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PrivateSubnet1CIDR: !Ref PrivateSubnet1CIDR + PrivateSubnet2CIDR: !Ref PrivateSubnet2CIDR + CreateAttachmentSubnets: true + AttachmentSubnet1CIDR: !Ref TgwSubnet1CIDR + AttachmentSubnet2CIDR: !Ref TgwSubnet2CIDR + InternalRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPCStack + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: Private Subnets Route Table + ClusterStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/cluster/tgw-ha.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnetA: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PublicSubnetB: !GetAtt VPCStack.Outputs.PublicSubnet2ID + PrivateSubnetA: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + PrivateSubnetB: !GetAtt VPCStack.Outputs.PrivateSubnet2ID + TgwHASubnetA: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + TgwHASubnetB: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/cluster/tgw-ha.yaml b/deprecated/aws/templates/R80.40/cluster/tgw-ha.yaml new file mode 100755 index 00000000..18b36563 --- /dev/null +++ b/deprecated/aws/templates/R80.40/cluster/tgw-ha.yaml @@ -0,0 +1,527 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point TGW HA Cluster into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnetA + - PublicSubnetB + - PrivateSubnetA + - PrivateSubnetB + - TgwHASubnetA + - TgwHASubnetB + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnetA: + default: Public subnet 1 + PublicSubnetB: + default: Public subnet 2 + PrivateSubnetA: + default: Private subnet 1 + PrivateSubnetB: + default: Private subnet 2 + TgwHASubnetA: + default: TGW HA subnet 1 + TgwHASubnetB: + default: TGW HA subnet 2 + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: you must select a VPC. + PublicSubnetA: + Description: Select a public subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the first Security Gateway. + PublicSubnetB: + Description: Select a public subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the second Security Gateway. + PrivateSubnetA: + Description: Select a private subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the first Security Gateway. + PrivateSubnetB: + Description: Select a private subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the second Security Gateway. + TgwHASubnetA: + Description: Select a TGW HA subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a TGW HA subnet for the first Security Gateway. + TgwHASubnetB: + Description: Select a TGW HA subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a TGW HAsubnet for the second Security Gateway. + InternalRouteTable: + Description: Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the Route Table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the Security Gateways. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: When choosing "false", make sure the cluster members can connect to an ec2 endpoint. + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Description: The license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to + get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between + Check Point components. Choose a random string consisting of at least 8 + alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: >- + Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + ClusterStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/cluster/geo-cluster.yaml + Parameters: + VPC: !Ref VPC + PublicSubnetA: !Ref PublicSubnetA + PublicSubnetB: !Ref PublicSubnetB + PrivateSubnetA: !Ref PrivateSubnetA + PrivateSubnetB: !Ref PrivateSubnetB + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary + TGWRouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: TGW Subnets + TGWDefaultRoute: + Type: AWS::EC2::Route + DependsOn: ClusterStack + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !GetAtt ClusterStack.Outputs.MemberAExternalInterface + RouteTableId: !Ref TGWRouteTable + TGWNSubnet1RouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: TGWRouteTable + Properties: + RouteTableId: !Ref TGWRouteTable + SubnetId: !Ref TgwHASubnetA + TGWSubnet2RouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: TGWRouteTable + Properties: + RouteTableId: !Ref TGWRouteTable + SubnetId: !Ref TgwHASubnetB +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/gateway/gateway-master.yaml b/deprecated/aws/templates/R80.40/gateway/gateway-master.yaml new file mode 100755 index 00000000..bca67151 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gateway/gateway-master.yaml @@ -0,0 +1,495 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Security Gateway into a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZone + - VPCCIDR + - PublicSubnetCIDR + - PrivateSubnetCIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewaySICKey + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - GatewayToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + - Label: + default: Automatic Provisioning with Security Management Server Settings (optional) + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + AvailabilityZone: + default: Availability zone + VPCCIDR: + default: VPC CIDR + PublicSubnetCIDR: + default: Public subnet CIDR + PrivateSubnetCIDR: + default: Private subnet CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Gateway Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateway Version & license + Shell: + default: Admin shell + GatewaySICKey: + default: Gateway SIC key + GatewayToken: + default: Smart-1 Cloud Token + GatewayPasswordHash: + default: Gateway Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + ControlGatewayOverPrivateOrPublicAddress: + default: Gateway address + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + AvailabilityZone: + Description: The availability zone in which to deploy the instance. + Type: AWS::EC2::AvailabilityZone::Name + MinLength: 1 + VPCCIDR: + Description: The CIDR block of the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnetCIDR: + Description: The public subnet of the Security Gateway. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnetCIDR: + Description: The private subnet of the Security Gateway. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The instance type of the Secutiry Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + NoEcho: true + GatewayToken: + Description: Follow the instructions in sk180501 to quickly connect this Gateway to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the Security Gateway is provisioned using its private. + or public address + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic. + provisioning configuration. + Type: String + ConfigurationTemplate: + Description: A name of a Security Gateway configuration template in the automatic. + provisioning configuration. + Type: String + MaxLength: 30 +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Ref AvailabilityZone + NumberOfAZs: 1 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnetCIDR + CreatePrivateSubnets: true + PrivateSubnet1CIDR: !Ref PrivateSubnetCIDR + CreateAttachmentSubnets: false + InternalRoutingTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalRoutingTable + InternalNetworkRouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref InternalRoutingTable + SubnetId: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + GatewayStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gateway/gateway.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnet: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PrivateSubnet: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + InternalRouteTable: !Ref InternalRoutingTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewaySICKey: !Ref GatewaySICKey + GatewayToken: !Ref GatewayToken + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate +Outputs: + CheckPointInstancePublicAddress: + Condition: AllocateAddress + Description: The public address of the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.PublicAddress + CheckPointInstancePrivateExternalAddress: + Description: The private external address of the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.PrivateExternalAddress + CheckPointInstancePrivateInternalAddress: + Description: The private internal address of the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.PrivateInternalAddress + CheckPointInstanceSSH: + Condition: AllocateAddress + Description: SSH command to the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.SSH + CheckPointInstanceURL: + Condition: AllocateAddress + Description: URL to the portal + Value: !GetAtt GatewayStack.Outputs.URL + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations + required to automatically provision the Gateways in the Auto Scaling Group, + such as what Security Policy to install and which Blades to enable, will be + placed under this template name. + Value: !Ref ConfigurationTemplate diff --git a/deprecated/aws/templates/R80.40/gateway/gateway.yaml b/deprecated/aws/templates/R80.40/gateway/gateway.yaml new file mode 100755 index 00000000..169f1239 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gateway/gateway.yaml @@ -0,0 +1,601 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Security Gateway into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnet + - PrivateSubnet + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewaySICKey + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - GatewayToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + - Label: + default: Automatic Provisioning with Security Management Server Settings (optional) + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + VPC: + default: VPC + PublicSubnet: + default: Public subnet + PrivateSubnet: + default: Private subnet + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Gateway Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateway Version & license + Shell: + default: Admin shell + GatewaySICKey: + default: Gateway SIC key + GatewayToken: + default: Smart-1 Cloud Token + GatewayPasswordHash: + default: Gateway Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + ControlGatewayOverPrivateOrPublicAddress: + default: Gateway address + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + VPC: + Type: AWS::EC2::VPC::Id + MinLength: 1 + PublicSubnet: + Description: The public subnet of the security gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + PrivateSubnet: + Description: The private subnet of the security gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + InternalRouteTable: + Description: The route table id in which to set 0.0.0.0/0 route to the Gateway instance (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Gateway, this requires manual configuration in the route table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + NoEcho: true + GatewayToken: + Description: Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + Type: String + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + NoEcho: true + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the Security Gateway is provisioned using its private + or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic + provisioning configuration. + Type: String + ConfigurationTemplate: + Description: A name of a Security Gateway configuration template in the automatic + provisioning configuration. + Type: String + MaxLength: 30 +Conditions: + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + ProvidedManagementParameters: !And [!Not [!Equals [!Ref ManagementServer, '']], !Not [!Equals [!Ref ConfigurationTemplate, '']]] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: AllocateAddress + DependsOn: GatewayInstance + Properties: + Handle: !Ref ReadyHandle + Timeout: 1800 + GatewayIAMRole: + Condition: EnableCloudWatch + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: [ ec2.amazonaws.com ] + Action: sts:AssumeRole + Path: / + GatewayInstanceProfile: + Condition: EnableCloudWatch + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [!Ref GatewayIAMRole] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName' ] + PolicyRole: !Ref GatewayIAMRole + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion,GW]] + ExternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - ExternalNetworkInterface + Description: eth0 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PublicSubnet + InternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalNetworkInterface + Description: eth1 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PrivateSubnet + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref InternalNetworkInterface + RouteTableId: !Ref InternalRouteTable + GatewayInstance: + Type: AWS::EC2::Instance + DependsOn: GatewayLaunchTemplate + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref GatewayLaunchTemplate + Version: !GetAtt GatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref GatewayName + - !If + - ProvidedManagementParameters + - Key: x-chkp-tags + Value: + !Join + - ':' + - - !Join ['=', [management, !Ref ManagementServer]] + - !Join ['=', [template,!Ref ConfigurationTemplate]] + - !Join ['=',[ip-address, !Ref ControlGatewayOverPrivateOrPublicAddress]] + - !Ref 'AWS::NoValue' + GatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref ExternalNetworkInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref InternalNetworkInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [EnableCloudWatch, !Ref GatewayInstanceProfile, !Ref 'AWS::NoValue'] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; hostname=${GatewayHostname} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; eic=${EnableInstanceConnect} ; eip=${AllocatePublicAddress} ; token=''${GatewayToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ReadyHandle}''',!Ref 'AWS::NoValue'] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${token}\"" installationType=\"gateway\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"gateway\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" allocatePublicAddress=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + PublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + AddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: GatewayInstance + Properties: + NetworkInterfaceId: !Ref ExternalNetworkInterface + AllocationId: !GetAtt PublicAddress.AllocationId + PrivateIpAddress: !GetAtt ExternalNetworkInterface.PrimaryPrivateIpAddress +Outputs: + PublicAddress: + Description: The public address of the Check Point instance. + Value: !Ref PublicAddress + Condition: AllocateAddress + PrivateExternalAddress: + Description: The private external address of the Check Point instance. + Value: !GetAtt ExternalNetworkInterface.PrimaryPrivateIpAddress + PrivateInternalAddress: + Description: The private internal address of the Check Point instance. + Value: !GetAtt InternalNetworkInterface.PrimaryPrivateIpAddress + SSH: + Description: SSH command to the Check Point instance. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref PublicAddress]] + Condition: AllocateAddress + URL: + Description: URL to the portal. + Value: !Join ['', ['https://', !Ref PublicAddress]] + Condition: AllocateAddress + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations + required to automatically provision the Gateways in the Auto Scaling Group, + such as what Security Policy to install and which Blades to enable, will be + placed under this template name. + Value: !Ref ConfigurationTemplate diff --git a/deprecated/aws/templates/R80.40/gateway/standalone-master.yaml b/deprecated/aws/templates/R80.40/gateway/standalone-master.yaml new file mode 100755 index 00000000..6408614d --- /dev/null +++ b/deprecated/aws/templates/R80.40/gateway/standalone-master.yaml @@ -0,0 +1,443 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys either a manually configurable or a Check Point CloudGuard IaaS + Security Gateway & Management (Standalone) instance in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZone + - VPCCIDR + - PublicSubnetCIDR + - PrivateSubnetCIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - StandaloneName + - StandaloneInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - StandaloneVersion + - Shell + - StandalonePasswordHash + - StandaloneMaintenancePasswordHash + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - StandaloneHostname + - AllowUploadDownload + - CloudWatch + - StandaloneBootstrapScript + - NTPPrimary + - NTPSecondary + - AdminCIDR + - GatewaysAddresses + ParameterLabels: + AvailabilityZone: + default: Availability zone + VPCCIDR: + default: VPC CIDR + PublicSubnetCIDR: + default: Public subnet CIDR + PrivateSubnetCIDR: + default: Private subnet CIDR + StandaloneName: + default: Standalone Name + StandaloneInstanceType: + default: Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + StandaloneVersion: + default: License + Shell: + default: Admin shell + StandalonePasswordHash: + default: Standalone Password hash + StandaloneMaintenancePasswordHash: + default: Gateway Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + StandaloneHostname: + default: Standalone Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + StandaloneBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses +Parameters: + AvailabilityZone: + Description: The availability zone in which to deploy the instance. + Type: AWS::EC2::AvailabilityZone::Name + MinLength: 1 + VPCCIDR: + Description: The CIDR block of the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnetCIDR: + Description: The public subnet of the Security Gateway. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnetCIDR: + Description: The private subnet of the Security Gateway. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + StandaloneName: + Type: String + Default: Check-Point-Instance + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Default: false + Type: String + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + StandaloneVersion: + Description: Standalone Version & License. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-PAYG-NGTP + - R80.40-BYOL + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + StandalonePasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + StandaloneMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + StandaloneInstanceType: + Description: The instance type of the Security Gateway & Management (Standalone) instance. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + StandaloneHostname: + Description: (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + StandaloneBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate. + with the Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Management. + Server. (optional) + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Ref AvailabilityZone + NumberOfAZs: 1 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnetCIDR + CreatePrivateSubnets: true + PrivateSubnet1CIDR: !Ref PrivateSubnetCIDR + CreateAttachmentSubnets: false + InternalRoutingTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalRoutingTable + InternalNetworkRouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref InternalRoutingTable + SubnetId: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + StandaloneStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gateway/standalone.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnet: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PrivateSubnet: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + InternalRouteTable: !Ref InternalRoutingTable + StandaloneName: !Ref StandaloneName + StandaloneInstanceType: !Ref StandaloneInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + StandaloneVersion: !Ref StandaloneVersion + Shell: !Ref Shell + StandalonePasswordHash: !Ref StandalonePasswordHash + StandaloneMaintenancePasswordHash: !Ref StandaloneMaintenancePasswordHash + ResourcesTagName: !Ref ResourcesTagName + StandaloneHostname: !Ref StandaloneHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + StandaloneBootstrapScript: !Ref StandaloneBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary + AdminCIDR: !Ref AdminCIDR + GatewaysAddresses: !Ref GatewaysAddresses +Outputs: + CheckPointInstancePublicAddress: + Condition: AllocateAddress + Description: The public address of the Check Point instance. + Value: !GetAtt StandaloneStack.Outputs.PublicAddress + CheckPointInstanceSSH: + Condition: AllocateAddress + Description: SSH command to the Check Point instance. + Value: !GetAtt StandaloneStack.Outputs.SSH + CheckPointInstanceURL: + Condition: AllocateAddress + Description: URL to the portal. + Value: !GetAtt StandaloneStack.Outputs.URL diff --git a/deprecated/aws/templates/R80.40/gateway/standalone.yaml b/deprecated/aws/templates/R80.40/gateway/standalone.yaml new file mode 100755 index 00000000..62ed02ce --- /dev/null +++ b/deprecated/aws/templates/R80.40/gateway/standalone.yaml @@ -0,0 +1,538 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys either a manually configurable or a Check Point CloudGuard IaaS + Security Gateway & Management (Standalone) instance into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnet + - PrivateSubnet + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - StandaloneName + - StandaloneInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - StandaloneVersion + - Shell + - StandalonePasswordHash + - StandaloneMaintenancePasswordHash + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - StandaloneHostname + - AllowUploadDownload + - CloudWatch + - StandaloneBootstrapScript + - NTPPrimary + - NTPSecondary + - AdminCIDR + - GatewaysAddresses + ParameterLabels: + VPC: + default: VPC + PublicSubnet: + default: Public subnet + PrivateSubnet: + default: Private subnet + InternalRouteTable: + default: Internal route table + StandaloneName: + default: Standalone Name + StandaloneInstanceType: + default: Standalone Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + StandaloneVersion: + default: License + Shell: + default: Admin shell + StandalonePasswordHash: + default: Standalone Password hash + StandaloneMaintenancePasswordHash: + default: Standalone Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + StandaloneHostname: + default: Standalone Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + StandaloneBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses +Parameters: + VPC: + Type: AWS::EC2::VPC::Id + MinLength: 1 + PublicSubnet: + Description: The public subnet of the Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + PrivateSubnet: + Description: The private subnet of the Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + InternalRouteTable: + Description: The route table id in which to set 0.0.0.0/0 route to the Security Gateway instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Gateway, this requires manual configuration in the route table. (optional) + Type: String + Default: '' + StandaloneName: + Type: String + Default: Check-Point-Instance + StandaloneInstanceType: + Description: The instance type of the Security Gateway & Management (Standalone) instance. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Default: false + Type: String + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + StandaloneVersion: + Description: Standalone Version & License. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-PAYG-NGTP + - R80.40-BYOL + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + StandalonePasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + StandaloneMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + StandaloneHostname: + Description: (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + StandaloneBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate. + with the Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Management. + Server. (optional) + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' +Conditions: + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + IsBYOL: !Equals [!Select [1, !Split ['-', !Ref StandaloneVersion]], 'BYOL'] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: AllocateAddress + DependsOn: StandaloneInstance + Properties: + Handle: !Ref ReadyHandle + Timeout: 1800 + StandaloneIAMRole: + Condition: EnableCloudWatch + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: [ ec2.amazonaws.com ] + Action: sts:AssumeRole + Path: / + StandaloneInstanceProfile: + Condition: EnableCloudWatch + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [ !Ref StandaloneIAMRole ] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName' ] + PolicyRole: !Ref StandaloneIAMRole + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !If [IsBYOL, !Join ['-', [!Ref StandaloneVersion,MGMT]], !Ref StandaloneVersion] + ExternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - ExternalNetworkInterface + Description: eth0 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PublicSubnet + InternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalNetworkInterface + Description: eth1 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PrivateSubnet + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref InternalNetworkInterface + RouteTableId: !Ref InternalRouteTable + StandaloneInstance: + Type: AWS::EC2::Instance + DependsOn: GatewayLaunchTemplate + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref GatewayLaunchTemplate + Version: !GetAtt GatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref StandaloneName + GatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref ExternalNetworkInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref InternalNetworkInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref StandaloneInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [ EnableCloudWatch, !Ref StandaloneInstanceProfile, !Ref 'AWS::NoValue' ] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; hostname=${StandaloneHostname} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; eic=${EnableInstanceConnect} ; eip=${AllocatePublicAddress} ; admin_subnet=${AdminCIDR}' + - !If [ AllocateAddress, !Sub ' wait_handle=''${ReadyHandle}''',!Ref 'AWS::NoValue' ] + - !Join [ '', [ ' bootstrap="$(echo ', 'Fn::Base64': !Ref StandaloneBootstrapScript, ')"' ] ] + - !Join [ '', [ ' pwd_hash="$(echo ', 'Fn::Base64': !Ref StandalonePasswordHash, ')"' ] ] + - !Join [ '', [ ' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref StandaloneMaintenancePasswordHash, ')"' ] ] + - !Sub [ ' version=${Version}', { Version: !Select [ 0, !Split [ '-', !Ref StandaloneVersion ] ] } ] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" installationType=\"standalone\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"standalone\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" adminSubnet=\"${admin_subnet}\" allocatePublicAddress=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + PublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + AddressAssoc: + Type: AWS::EC2::EIPAssociation + DependsOn: StandaloneInstance + Condition: AllocateAddress + Properties: + NetworkInterfaceId: !Ref ExternalNetworkInterface + AllocationId: !GetAtt PublicAddress.AllocationId + PrivateIpAddress: !GetAtt ExternalNetworkInterface.PrimaryPrivateIpAddress +Outputs: + PublicAddress: + Condition: AllocateAddress + Description: The public address of the Check Point instance. + Value: !Ref PublicAddress + SSH: + Condition: AllocateAddress + Description: SSH command to the Check Point instance. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref PublicAddress]] + URL: + Condition: AllocateAddress + Description: URL to the portal. + Value: !Join ['', ['https://', !Ref PublicAddress ]] diff --git a/deprecated/aws/templates/R80.40/gwlb/amis-gwlb.yaml b/deprecated/aws/templates/R80.40/gwlb/amis-gwlb.yaml new file mode 100755 index 00000000..08089c1f --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/amis-gwlb.yaml @@ -0,0 +1,123 @@ +AWSTemplateFormatVersion: '2010-09-09' +Description: Returns a Check Point Amazon Machine ID (__VERSION__) +Parameters: + Version: + Description: Security Gateway version + Type: String + Default: R80.40-BYOL-GW + AllowedValues: + - R80.40-BYOL-GW + - R80.40-PAYG-NGTP-GW + - R80.40-PAYG-NGTX-GW +Mappings: + ConverterMap: + R80.40-BYOL-GW: + Value: R8040BYOLGW + R80.40-PAYG-NGTP-GW: + Value: R8040PAYGNGTPGW + R80.40-PAYG-NGTX-GW: + Value: R8040PAYGNGTXGW + RegionMap: + af-south-1: + R8040BYOLGW: ami-0ac3de5e02318dbb9 + R8040PAYGNGTPGW: ami-0bd5e19d8b6c2e010 + R8040PAYGNGTXGW: ami-0daea7d32748a95b7 + ap-east-1: + R8040BYOLGW: ami-03e84cc92d6d806d9 + R8040PAYGNGTPGW: ami-0a50d8be138a39ffa + R8040PAYGNGTXGW: ami-07b3af199dfa93478 + ap-northeast-1: + R8040BYOLGW: ami-08b50c5e55789267c + R8040PAYGNGTPGW: ami-07ed13ea6074c0487 + R8040PAYGNGTXGW: ami-04691498c292bb2ca + ap-northeast-2: + R8040BYOLGW: ami-0199c1aa2899f1fc2 + R8040PAYGNGTPGW: ami-07f249c288d5453e5 + R8040PAYGNGTXGW: ami-0de1b8fb057fc6cb3 + ap-northeast-3: + R8040BYOLGW: ami-0001e1915cbd7af1b + R8040PAYGNGTPGW: ami-05e34615518b20617 + R8040PAYGNGTXGW: ami-05d2bb2f12a0bb254 + ap-south-1: + R8040BYOLGW: ami-0a26838410046600b + R8040PAYGNGTPGW: ami-012277a3c7c028020 + R8040PAYGNGTXGW: ami-03da4b399784399f0 + ap-south-2: {} + ap-southeast-1: + R8040BYOLGW: ami-0af3307d70bf9d8b6 + R8040PAYGNGTPGW: ami-0e8ed0eb9aa094877 + R8040PAYGNGTXGW: ami-0accd2e7ebac4ed10 + ap-southeast-2: + R8040BYOLGW: ami-054952950277df882 + R8040PAYGNGTPGW: ami-0c483bfb4f071bbb3 + R8040PAYGNGTXGW: ami-0a6030b227d947535 + ap-southeast-3: + R8040BYOLGW: ami-01de813d939f37210 + R8040PAYGNGTPGW: ami-0a69ac977555b13e4 + R8040PAYGNGTXGW: ami-0d730e1b951919c9b + ca-central-1: + R8040BYOLGW: ami-0d71e4ca01e67dc40 + R8040PAYGNGTPGW: ami-0c2116d978c175f8a + R8040PAYGNGTXGW: ami-0e53f675371e80935 + eu-central-1: + R8040BYOLGW: ami-046f3dfde3055c0c2 + R8040PAYGNGTPGW: ami-06af9b32f93c957dc + R8040PAYGNGTXGW: ami-09c6fee62f6bc0270 + eu-central-2: {} + eu-north-1: + R8040BYOLGW: ami-05c9b72e460f6e230 + R8040PAYGNGTPGW: ami-09399d091a241d03e + R8040PAYGNGTXGW: ami-08422e2787d7a0b86 + eu-south-1: + R8040BYOLGW: ami-0021d29e6c8983ff6 + R8040PAYGNGTPGW: ami-07c770caf8d288636 + R8040PAYGNGTXGW: ami-0b355610d679e47bc + eu-south-2: {} + eu-west-1: + R8040BYOLGW: ami-00be1913a17d99fb4 + R8040PAYGNGTPGW: ami-0b53953de2f981cc3 + R8040PAYGNGTXGW: ami-0f9c751772234a142 + eu-west-2: + R8040BYOLGW: ami-05aec4880e95365ce + R8040PAYGNGTPGW: ami-036cdb2393d5c1a32 + R8040PAYGNGTXGW: ami-09891046424c314af + eu-west-3: + R8040BYOLGW: ami-02b95b5c9683bd9ac + R8040PAYGNGTPGW: ami-033f58324df30157a + R8040PAYGNGTXGW: ami-0c43d0326c68bcb48 + me-central-1: + R8040BYOLGW: ami-02e8d091194949457 + R8040PAYGNGTPGW: ami-0a8131eea457f8a71 + R8040PAYGNGTXGW: ami-04ab9b46aa75ad99b + me-south-1: + R8040BYOLGW: ami-0b95f19ae216bdf25 + R8040PAYGNGTPGW: ami-0328604c962b84b4c + R8040PAYGNGTXGW: ami-0455013fffc60b073 + sa-east-1: + R8040BYOLGW: ami-0e875f613b36b6b79 + R8040PAYGNGTPGW: ami-008379899b3dc952d + R8040PAYGNGTXGW: ami-07e9fc0a27d0eb659 + us-east-1: + R8040BYOLGW: ami-038bddea5b07efcd2 + R8040PAYGNGTPGW: ami-0f51f2cc69296c954 + R8040PAYGNGTXGW: ami-056bc408f66e8057b + us-east-2: + R8040BYOLGW: ami-0c90634daf216611a + R8040PAYGNGTPGW: ami-04c93712f9f3c54ca + R8040PAYGNGTXGW: ami-0b6988dff7d7b520b + us-west-1: + R8040BYOLGW: ami-0ee766db82ecd8c06 + R8040PAYGNGTPGW: ami-0a86fb5df6b87b3ee + R8040PAYGNGTXGW: ami-07b7818ac041a88a6 + us-west-2: + R8040BYOLGW: ami-0271bf8fd0aae0f14 + R8040PAYGNGTPGW: ami-0595481bb41b3ec7d + R8040PAYGNGTXGW: ami-0e6c6921c23256796 +Resources: + DummyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Properties: {} +Outputs: + ImageId: + Description: Check Point Security Gateway AMI + Value: !FindInMap [RegionMap ,!Ref 'AWS::Region', !FindInMap [ConverterMap, !Ref 'Version', Value]] diff --git a/deprecated/aws/templates/R80.40/gwlb/autoscale-gwlb.yaml b/deprecated/aws/templates/R80.40/gwlb/autoscale-gwlb.yaml new file mode 100755 index 00000000..725be55c --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/autoscale-gwlb.yaml @@ -0,0 +1,657 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Create an Auto Scaling group of Check Point gateways (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - GatewaysSubnets + - Label: + default: EC2 Instances Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - VolumeSize + - VolumeType + - EnableVolumeEncryption + - EnableInstanceConnect + - MetaDataToken + - Label: + default: Auto Scaling Configuration + Parameters: + - GatewaysMinSize + - GatewaysMaxSize + - AdminEmail + - GatewaysTargetGroups + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - Label: + default: Automatic Provisioning with Security Management Server Settings + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - AllocatePublicAddress + - ManagementServer + - ConfigurationTemplate + - Label: + default: Proxy Configuration (optional) + Parameters: + - ELBType + - ELBPort + - ELBClients + ParameterLabels: + VPC: + default: VPC + GatewaysSubnets: + default: Gateways subnets + GatewayName: + default: Gateways name + GatewayInstanceType: + default: Gateways instance type + KeyName: + default: Key name + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableVolumeEncryption: + default: Enable volume encryption + EnableInstanceConnect: + default: Enable AWS Instance Connect + MetaDataToken: + default: Metadata HTTP token + GatewaysMinSize: + default: Minimum Gateway group size + GatewaysMaxSize: + default: Maximum Gateway group size + AdminEmail: + default: Email address + GatewaysTargetGroups: + default: Gateways target groups + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Gateways bootstrap script + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + AllocatePublicAddress: + default: Allocate Public IPs + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + ELBType: + default: Proxy type + ELBPort: + default: Proxy port + ELBClients: + default: Allowed proxy clients +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + GatewaysSubnets: + Description: Select at least 2 public subnets in the VPC. + Type: List + MinLength: 2 + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The instance type of the Secutiry Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableVolumeEncryption: + Description: Encrypt Auto Scaling instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewaysMinSize: + Description: The minimal number of gateways in the Auto Scaling group. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of gateways in the Auto Scaling group. + Type: Number + Default: 10 + MinValue: 1 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + ConstraintDescription: Must be a valid email address. + GatewaysTargetGroups: + Description: A list of Target Groups to associate with the Auto Scaling + group (comma separated list of ARNs, without spaces). (optional) + Type: String + Default: '' + GatewayVersion: + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + AllocatePublicAddress: + Description: Allocate a Public IP for gateway members. + Type: String + Default: false + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: ASG-configuration + MinLength: 1 + MaxLength: 30 + ELBType: + Type: String + Default: none + AllowedValues: + - none + - internal + - internet-facing + ELBPort: + Type: Number + Default: 8080 + ELBClients: + Type: String + Default: 0.0.0.0/0 + AllowedPattern: '^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})/(\d{1,2})$' +Conditions: + ProvidedAdminEmail: !Not [!Equals [!Ref AdminEmail, '']] + ProvidedTargetGroups: !Not [!Equals [!Ref GatewaysTargetGroups, '']] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + CreateELB: !Not [!Equals [!Ref ELBType, none]] + isR8040: !Or [!Equals [!Ref GatewayVersion,R80.40-BYOL], !Equals [!Ref GatewayVersion, R80.40-PAYG-NGTP], !Equals [!Ref GatewayVersion,R80.40-PAYG-NGTX]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ChkpGatewayRole: + Type: AWS::IAM::Role + Condition: EnableCloudWatch + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: + - ec2.amazonaws.com + Action: + - sts:AssumeRole + Path: / + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: ChkpGatewayPolicy + PolicyRole: !Ref ChkpGatewayRole + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: EnableCloudWatch + Properties: + Path: / + Roles: + - !Ref ChkpGatewayRole + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion, GW]] + NotificationTopic: + Type: AWS::SNS::Topic + Condition: ProvidedAdminEmail + Properties: + Subscription: + - Endpoint: !Ref AdminEmail + Protocol: email + ElasticLoadBalancer: + Type: AWS::ElasticLoadBalancing::LoadBalancer + Condition: CreateELB + Properties: + CrossZone: true + Listeners: + - LoadBalancerPort: !Ref ELBPort + InstancePort: !Ref ELBPort + Protocol: TCP + HealthCheck: + Target: !Join [':', [TCP, !Ref ELBPort]] + HealthyThreshold: 3 + UnhealthyThreshold: 5 + Interval: 30 + Timeout: 5 + Scheme: !Ref ELBType + Subnets: !Ref GatewaysSubnets + Policies: + - PolicyName: EnableProxyProtocol + PolicyType: ProxyProtocolPolicyType + Attributes: + - Name: ProxyProtocol + Value: true + InstancePorts: + - !Ref ELBPort + SecurityGroups: + - !Ref ELBSecurityGroup + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + Tags: + - Key: Name + Value: !Join ['_', [!Ref 'AWS::StackName', PermissiveSecurityGroup]] + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + GatewayGroup: + Type: AWS::AutoScaling::AutoScalingGroup + DependsOn: GatewayLaunchTemplate + Properties: + VPCZoneIdentifier: !Ref GatewaysSubnets + LaunchTemplate: + LaunchTemplateId: !Ref GatewayLaunchTemplate + Version: !GetAtt GatewayLaunchTemplate.LatestVersionNumber + MinSize: !Ref GatewaysMinSize + MaxSize: !Ref GatewaysMaxSize + LoadBalancerNames: !If [CreateELB, [!Ref ElasticLoadBalancer], !Ref 'AWS::NoValue'] + TargetGroupARNs: !If [ProvidedTargetGroups, !Split [',', !Ref GatewaysTargetGroups], !Ref 'AWS::NoValue'] + HealthCheckGracePeriod: 3600 + HealthCheckType: ELB + NotificationConfiguration: !If + - ProvidedAdminEmail + - TopicARN: !Ref NotificationTopic + NotificationTypes: + - autoscaling:EC2_INSTANCE_LAUNCH + - autoscaling:EC2_INSTANCE_LAUNCH_ERROR + - autoscaling:EC2_INSTANCE_TERMINATE + - autoscaling:EC2_INSTANCE_TERMINATE_ERROR + - !Ref 'AWS::NoValue' + Tags: + - Key: Name + Value: !Ref GatewayName + PropagateAtLaunch: true + - Key: x-chkp-tags + Value: !Join + - ':' + - - !Join ['=', [management, !Ref ManagementServer]] + - !Join ['=', [template, !Ref ConfigurationTemplate]] + - !Join ['=', [ip-address, !Ref ControlGatewayOverPrivateOrPublicAddress]] + PropagateAtLaunch: true + - Key: x-chkp-topology + Value: internal + PropagateAtLaunch: true + - Key: x-chkp-solution + Value: autoscale_gwlb + PropagateAtLaunch: true + GatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: !Ref AllocatePublicAddress + Groups: + - !Ref PermissiveSecurityGroup + Monitoring: + Enabled: true + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [EnableCloudWatch, !Ref InstanceProfile, !Ref 'AWS::NoValue'] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'network:' + - ' version: 1' + - ' config:' + - ' - type: bridge' + - ' name: br0' + - ' mtu: *eth0-mtu' + - ' subnets:' + - ' - address: *eth0-private' + - ' type: static' + - ' gateway: *default-gateway' + - ' dns_nameservers:' + - ' - *eth0-dns1' + - ' bridge_interfaces:' + - ' - eth0' + - 'kernel_parameters:' + - ' sim:' + - ' - sim_geneve_enabled=1' + - ' - sim_geneve_br_dev=br0' + - ' fw:' + - ' - fwtls_bridge_mode_inspection=1' + - ' - fw_geneve_enabled=1' + - 'bootcmd:' + - ' - echo "brctl hairpin br0 eth0 on" >> /etc/rc.local' + - ' - echo "cpprod_util CPPROD_SetValue \"fw1\" \"AwsGwlb\" 4 1 1" >> /etc/rc.local' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect}' + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" sicKey=\"${sic}\" installationType=\"autoscale\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"autoscale_gwlb\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + GatewayScaleUpPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref GatewayGroup + Cooldown: 300 + ScalingAdjustment: 1 + GatewayScaleDownPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref GatewayGroup + Cooldown: 300 + ScalingAdjustment: -1 + CPUAlarmHigh: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-up if CPU > 80% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 80 + AlarmActions: + - !Ref GatewayScaleUpPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref GatewayGroup + ComparisonOperator: GreaterThanThreshold + CPUAlarmLow: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-down if CPU < 60% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 60 + AlarmActions: + - !Ref GatewayScaleDownPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref GatewayGroup + ComparisonOperator: LessThanThreshold + ELBSecurityGroup: + Type: AWS::EC2::SecurityGroup + Condition: CreateELB + Properties: + GroupDescription: ELB security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: tcp + CidrIp: !Ref ELBClients + FromPort: !Ref ELBPort + ToPort: !Ref ELBPort +Outputs: + URL: + Description: The URL of the Proxy. + Condition: CreateELB + Value: !Join ['', ['http://', !GetAtt ElasticLoadBalancer.DNSName]] + SecurityGroup: + Description: The Security Group of the Auto Scaling group. + Value: !GetAtt PermissiveSecurityGroup.GroupId +Rules: + GatewayAddressAllocationRule: + RuleCondition: !Equals [!Ref ControlGatewayOverPrivateOrPublicAddress, 'public'] + Assertions: + - AssertDescription: "Gateway's selected to be provisioned by public IP, but ['AllocatePublicAddress'] parameter is false" + Assert: !Equals [!Ref AllocatePublicAddress, 'true'] diff --git a/deprecated/aws/templates/R80.40/gwlb/cme-iam-role-gwlb.yaml b/deprecated/aws/templates/R80.40/gwlb/cme-iam-role-gwlb.yaml new file mode 100755 index 00000000..be7c923c --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/cme-iam-role-gwlb.yaml @@ -0,0 +1,131 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for selected permissions (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: IAM + Parameters: + - Permissions + - Label: + default: Advanced Configuration (optional) + Parameters: + - STSRoles + - TrustedAccount + ParameterLabels: + Permissions: + default: IAM role + STSRoles: + default: STS roles + TrustedAccount: + default: Trusted Account ID +Parameters: + Permissions: + Type: String + Default: Create with read permissions + AllowedValues: + - Create with read permissions + - Create with read-write permissions + - Create with assume role permissions (specify an STS role ARN) + STSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated list of ARNs, without spaces). + Type: String + Default: '' + TrustedAccount: + Description: A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it. + Type: String + Default: '' + AllowedPattern: '^([0-9]{12})|$' +Conditions: + AllowReadPermissions: !Or + - !Equals [!Ref Permissions, Create with read permissions] + - !Equals [!Ref Permissions, Create with read-write permissions] + AllowWritePermissions: !Equals [!Ref Permissions, Create with read-write permissions] + ProvidedSTSRoles: !Not [!Equals [!Ref STSRoles, '']] + NotProvidedTrustedAccount: !Equals ['', !Ref TrustedAccount] + ProvidedTrustedAccount: !Not [!Condition NotProvidedTrustedAccount] +Resources: + CMEIAMRole: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - ProvidedTrustedAccount + - Effect: Allow + Principal: + AWS: [!Ref TrustedAccount] + Action: ['sts:AssumeRole'] + - !Ref 'AWS::NoValue' + - !If + - NotProvidedTrustedAccount + - Effect: Allow + Principal: + Service: [ec2.amazonaws.com] + Action: ['sts:AssumeRole'] + - !Ref 'AWS::NoValue' + Path: / + Policies: + - PolicyName: CMEPolicy + PolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - ProvidedSTSRoles + - Effect: Allow + Action: ['sts:AssumeRole'] + Resource: !Split [',', !Ref STSRoles] + - !Ref 'AWS::NoValue' + - !If + - AllowReadPermissions + - Effect: Allow + Action: + - autoscaling:DescribeAutoScalingGroups + - ec2:DescribeRegions + - ec2:DescribeInstances + - ec2:DescribeNetworkInterfaces + - ec2:DescribeRouteTables + - ec2:DescribeSecurityGroups + - ec2:DescribeSubnets + - ec2:DescribeVpcs + - ec2:DescribeInternetGateways + - ec2:DescribeVpcEndpoints + - ec2:DescribeVpcEndpointServiceConfigurations + - elasticloadbalancing:DescribeLoadBalancers + - elasticloadbalancing:DescribeTags + - elasticloadbalancing:DescribeListeners + - elasticloadbalancing:DescribeTargetGroups + - elasticloadbalancing:DescribeRules + - elasticloadbalancing:DescribeTargetHealth + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowWritePermissions + - Effect: Allow + Action: + - ec2:CreateRoute + - ec2:ReplaceRoute + - ec2:DeleteRoute + - ec2:CreateRouteTable + - ec2:AssociateRouteTable + - ec2:CreateTags + Resource: '*' + - !Ref 'AWS::NoValue' + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + InstanceProfileName: !Ref CMEIAMRole + Roles: + - !Ref CMEIAMRole +Outputs: + CMEIAMRole: + Description: The IAM role. + Value: !Ref CMEIAMRole + CMEARNRole: + Description: The IAM role ARN. + Value: !GetAtt CMEIAMRole.Arn + InstanceProfile: + Description: The Instance Profile ARN. + Value: !GetAtt InstanceProfile.Arn + diff --git a/deprecated/aws/templates/R80.40/gwlb/gwlb-master.yaml b/deprecated/aws/templates/R80.40/gwlb/gwlb-master.yaml new file mode 100755 index 00000000..581341f8 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/gwlb-master.yaml @@ -0,0 +1,732 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - AcceptConnectionRequired + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - AllocatePublicAddress + - CloudWatch + - GatewayBootstrapScript + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Auto Scaling Group Public Subnet 1 + PublicSubnet2CIDR: + default: Auto Scaling Group Public Subnet 2 + PublicSubnet3CIDR: + default: Auto Scaling Group Public Subnet 3 + PublicSubnet4CIDR: + default: Auto Scaling Group Public Subnet 4 + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + AcceptConnectionRequired: + default: Connection Acceptance Required + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + AllocatePublicAddress: + default: Allocate Public IPs + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Gateways bootstrap script + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + AvailabilityZones: + Description: List of Availability Zones (AZs) to use for the subnets in the VPC. Select at least two. + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + VPCCIDR: + Description: CIDR block for the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. If you choose to deploy a Security Management Server it will be deployed in this subnet. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet3CIDR: + Description: CIDR block for public subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet4CIDR: + Description: CIDR block for public subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: gwlb-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: gwlb-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + AllowedPattern: '^([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])$' + Default: gwlb1 + MaxLength: 32 + ConstraintDescription: Must be a valid GWLB Name. + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + AllowedPattern: '^([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])$' + Default: tg1 + MaxLength: 32 + ConstraintDescription: Must be a valid target group name. + AcceptConnectionRequired: + Description: Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). + Default: "false" + AllowedValues: ["true", "false"] + Type: String + ConstraintDescription: Must be true or false. + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + AllocatePublicAddress: + Description: Allocate a Public IP for gateway members. + Type: String + Default: false + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group. + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',' , !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PublicSubnet3CIDR: !Ref PublicSubnet3CIDR + PublicSubnet4CIDR: !Ref PublicSubnet4CIDR + CreatePrivateSubnets: false + GWLBStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/gwlb.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + GatewaysSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.PublicSubnet1ID + - !GetAtt VPCStack.Outputs.PublicSubnet2ID + - !If [3AZs, !GetAtt VPCStack.Outputs.PublicSubnet3ID, !Ref 'AWS::NoValue'] + - !If [4AZs, !GetAtt VPCStack.Outputs.PublicSubnet4ID, !Ref 'AWS::NoValue'] + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + AllowUploadDownload: !Ref AllowUploadDownload + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + AdminEmail: !Ref AdminEmail + Shell: !Ref Shell + GWLBName: !Ref GWLBName + TargetGroupName: !Ref TargetGroupName + AcceptConnectionRequired: !Ref AcceptConnectionRequired + CrossZoneLoadBalancing: !Ref CrossZoneLoadBalancing + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + AllocatePublicAddress: !Ref AllocatePublicAddress + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + GatewaysPolicy: !Ref GatewaysPolicy + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses +Outputs: + VPCID: + Description: VPC ID. + Value: !GetAtt VPCStack.Outputs.VPCID + ManagementPublicAddress: + Description: The public address of the management server. + Value: !GetAtt GWLBStack.Outputs.ManagementPublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !GetAtt GWLBStack.Outputs.ConfigurationTemplateName + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name + Value: !GetAtt GWLBStack.Outputs.ControllerName + GWLBName: + Description: Gateway Load Balancer Name. + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name. + Value: !GetAtt GWLBStack.Outputs.GWLBServiceName +Rules: + GatewayAddressAllocationRule: + RuleCondition: !Equals [!Ref ControlGatewayOverPrivateOrPublicAddress, 'public'] + Assertions: + - AssertDescription: "Gateway's selected to be provisioned by public IP, but ['AllocatePublicAddress'] parameter is false" + Assert: !Equals [!Ref AllocatePublicAddress, 'true'] diff --git a/deprecated/aws/templates/R80.40/gwlb/gwlb-servers-infrastructure.yaml b/deprecated/aws/templates/R80.40/gwlb/gwlb-servers-infrastructure.yaml new file mode 100755 index 00000000..2f90dd34 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/gwlb-servers-infrastructure.yaml @@ -0,0 +1,324 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy GWLB application servers infrastructure, it creates a Multi-AZ, multi-subnet VPC infrastructure for application servers, and Multi-AZ, multi-subnet VPC infrastructure for GWLBe, and optionally deploy Application Autoscale(__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Availability Zone Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - Label: + default: Server Network Configuration + Parameters: + - VPCCIDR + - Label: + default: Server Network Configuration + Parameters: + - VPCCIDR + - ServersSubnet1CIDR + - ServersSubnet2CIDR + - ServersSubnet3CIDR + - ServersSubnet4CIDR + - GWLBeSubnet1CIDR + - GWLBeSubnet2CIDR + - GWLBeSubnet3CIDR + - GWLBeSubnet4CIDR + - Label: + default: GWLB Information + Parameters: + - SubnetTagsInboundCIDR + - SubnetTagsOutboundCIDR + - GWLBServiceName + - Label: + default: Web Servers Auto Scaling Group Configuration + Parameters: + - ServersDeploy + - AdminEmail + - ServerAMI + - KeyName + - GroupMinSize + - GroupMaxSize + - ALBProtocol + - ServicePort + - ServerInstanceType + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of Availability Zones + VPCCIDR: + default: Servers VPC CIDR + ServersSubnet1CIDR: + default: Servers subnet 1 CIDR + ServersSubnet2CIDR: + default: Servers subnet 2 CIDR + ServersSubnet3CIDR: + default: Servers subnet 3 CIDR + ServersSubnet4CIDR: + default: Servers subnet 4 CIDR + GWLBeSubnet1CIDR: + default: GWLBe subnet 1 CIDR + GWLBeSubnet2CIDR: + default: GWLBe subnet 2 CIDR + GWLBeSubnet3CIDR: + default: GWLBe subnet 3 CIDR + GWLBeSubnet4CIDR: + default: GWLBe subnet 4 CIDR + SubnetTagsInboundCIDR: + default: App cidr inbound tags + SubnetTagsOutboundCIDR: + default: App cidr Outbound tags + GWLBServiceName: + defsult: GWLB Service Name + ALBProtocol: + default: ALB Protocol + ServicePort: + default: Custom service port + ServersDeploy: + default: Deploy servers + ServerInstanceType: + default: Servers instance type + ServerAMI: + default: AMI ID + GroupMinSize: + default: Minimum group size + GroupMaxSize: + default: Maximum group size + AdminEmail: + default: Email address + KeyName: + default: Key name +Parameters: + AvailabilityZones: + Description: 'List of Availability Zones to use for the subnets in the VPC. Note: The logical order is preserved.' + Type: List + MinLength: 1 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your + selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 1 + MaxValue: 4 + VPCCIDR: + Description: CIDR block for the Servers VPC. + Type: String + Default: 192.168.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + ServersSubnet1CIDR: + Description: CIDR block for the public DMZ subnet 1 located in Availability Zone 1. + Type: String + Default: 192.168.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + ServersSubnet2CIDR: + Description: CIDR block for the public DMZ subnet 2 located in Availability Zone 2. + Type: String + Default: 192.168.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + ServersSubnet3CIDR: + Description: CIDR block for the public DMZ subnet 3 located in Availability Zone 3. + Type: String + Default: 192.168.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + ServersSubnet4CIDR: + Description: CIDR block for the public DMZ subnet 4 located in Availability Zone 4. + Type: String + Default: 192.168.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet1CIDR: + Description: CIDR block for the GWLBe subnet 1 located in Availability Zone 1. + Type: String + Default: 192.168.70.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet2CIDR: + Description: CIDR block for the GWLBe subnet 2 located in Availability Zone 2. + Type: String + Default: 192.168.80.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet3CIDR: + Description: CIDR block for the GWLBe subnet 3 located in Availability Zone 3. + Type: String + Default: 192.168.90.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet4CIDR: + Description: CIDR block for the GWLBe subnet 4 located in Availability Zone 4. + Type: String + Default: 192.168.100.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + SubnetTagsInboundCIDR: + Description: Inbound Subnet tagging for Inspection (Comma-delimited list of three CIDR blocks for inspection) + Type: CommaDelimitedList + Default: "0.0.0.0/0" + SubnetTagsOutboundCIDR: + Description: Outbound Subnet tagging for Inspection (Comma-delimited list of three CIDR blocks for inspection) + Type: CommaDelimitedList + Default: "0.0.0.0/0" + GWLBServiceName: + Description: GWLB service name (The value can be achieved from security VPC stack outputs) + Type: String + GroupMinSize: + Description: The minimal number of Application Servers. + Type: Number + Default: 2 + MinValue: 1 + GroupMaxSize: + Description: The maximal number of Application Servers. + Type: Number + Default: 10 + MinValue: 1 + ALBProtocol: + Description: The protocol to use on the Application Load Balancer. If Network Load Balancer was selected this section will be ignored. + Type: String + Default: HTTP + AllowedValues: + - HTTP + - HTTPS + ServicePort: + Description: 'The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS.' + Type: String + AllowedPattern: '^([0-9]{1,4}|[1-5][0-9]{4}|6[0-4][0-9]{3}|65[0-4][0-9]{2}|655[0-2][0-9]|6553[0-5])?$' + ConstraintDescription: Custom service port must be a number between 0 and 65535. + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + ServersDeploy: + Description: Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored. + Type: String + Default: false + AllowedValues: + - true + - false + ServerInstanceType: + Description: The EC2 instance type for the web servers. + Type: String + Default: t3.micro + AllowedValues: + - t3.nano + - t3.micro + - t3.small + - t3.medium + - t3.large + - t3.xlarge + - t3.2xlarge + ConstraintDescription: Must be a valid EC2 instance type. + ServerAMI: + Description: The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63). + Type: String + AllowedPattern: '^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$' + ConstraintDescription: Amazon Machine Image ID must be in the form ami-xxxxxxxx or ami-xxxxxxxxxxxxxxxxx. + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + 2AZs: !Or [!Equals [!Ref NumberOfAZs, 2], !Condition 3AZs] + DeployServers: !Equals [!Ref ServersDeploy, true] + EncryptedProtocol: !Equals [ ALBProtocol, HTTPS ] + ProvidedPort: !Not [!Equals [!Ref ServicePort, '']] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/qs-gwlb-servers-vpc.yaml + Parameters: + AvailabilityZones: !Join [ ',' , !Ref AvailabilityZones ] + NumberOfAZs: !Ref NumberOfAZs + VPCCIDR: !Ref VPCCIDR + ServersSubnet1CIDR: !Ref ServersSubnet1CIDR + ServersSubnet2CIDR: !Ref ServersSubnet2CIDR + ServersSubnet3CIDR: !Ref ServersSubnet3CIDR + ServersSubnet4CIDR: !Ref ServersSubnet4CIDR + GWLBeSubnet1CIDR: !Ref GWLBeSubnet1CIDR + GWLBeSubnet2CIDR: !Ref GWLBeSubnet2CIDR + GWLBeSubnet3CIDR: !Ref GWLBeSubnet3CIDR + GWLBeSubnet4CIDR: !Ref GWLBeSubnet4CIDR + SubnetTagsOutboundCIDR: !Join [ ',' , !Ref SubnetTagsOutboundCIDR ] + SubnetTagsInboundCIDR: !Join [ ',' , !Ref SubnetTagsInboundCIDR ] + GWLBeEndpointStack: + Type: AWS::CloudFormation::Stack + DependsOn: VPCStack + Properties: + TemplateURL: __URL__/gwlb/qs-gwlb-endpoints.yaml + Parameters: + NumberOfAZs: !Ref NumberOfAZs + GWLBeVPC: !GetAtt VPCStack.Outputs.VPCID + GWLBeSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.GWLBeSubnet1ID + - !GetAtt VPCStack.Outputs.GWLBeSubnet2ID + - !If [ 3AZs, !GetAtt VPCStack.Outputs.GWLBeSubnet3ID, !Ref 'AWS::NoValue' ] + - !If [ 4AZs, !GetAtt VPCStack.Outputs.GWLBeSubnet4ID, !Ref 'AWS::NoValue' ] + GWLBServiceName: !Ref GWLBServiceName + ServersSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.ServersSubnet1ID + - !GetAtt VPCStack.Outputs.ServersSubnet2ID + - !If [ 3AZs, !GetAtt VPCStack.Outputs.ServersSubnet3ID, !Ref 'AWS::NoValue' ] + - !If [ 4AZs, !GetAtt VPCStack.Outputs.ServersSubnet4ID, !Ref 'AWS::NoValue' ] + ServersCIDRs: !Join + - ',' + - - !Ref ServersSubnet1CIDR + - !Ref ServersSubnet2CIDR + - !If [ 3AZs, !Ref ServersSubnet3CIDR, !Ref 'AWS::NoValue' ] + - !If [ 4AZs, !Ref ServersSubnet4CIDR, !Ref 'AWS::NoValue' ] + ServerIGW: !GetAtt VPCStack.Outputs.IGWID + ServersStacks: + Type: AWS::CloudFormation::Stack + Condition: DeployServers + DependsOn: GWLBeEndpointStack + Properties: + TemplateURL: __URL__/gwlb/qs-gwlb-servers-autoscale.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + Subnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.ServersSubnet1ID + - !GetAtt VPCStack.Outputs.ServersSubnet2ID + - !If [ 3AZs, !GetAtt VPCStack.Outputs.ServersSubnet3ID, !Ref 'AWS::NoValue' ] + - !If [ 4AZs, !GetAtt VPCStack.Outputs.ServersSubnet4ID, !Ref 'AWS::NoValue' ] + ResourcesTagName: !Ref ResourcesTagName + ALBProtocol: !Ref ALBProtocol + ServicePort: !If [ProvidedPort, !Ref ServicePort, !If [EncryptedProtocol, 443, 80]] + AdminEmail: !Ref AdminEmail + ServerInstanceType: !Ref ServerInstanceType + ServerAMI: !Ref ServerAMI + KeyName: !Ref KeyName + AllocateServerPublicAddress: true + ServersMinSize: !Ref GroupMinSize + ServersMaxSize: !Ref GroupMaxSize +Outputs: + VpcEndpointService: + Description: Endpoint Service Name. + Value: !GetAtt VPCStack.Outputs.VPCID + ServerPorts: + Description: The internal Load Balancer should listen to this port. + Value: !If [EncryptedProtocol, 443, 80] + Condition: DeployServers + ServerLBURL: + Description: The URL of the Servers Application Load Balancer. + Value: !GetAtt ServersStacks.Outputs.ServerLBURL + Condition: DeployServers + ServerSecurityGroupID: + Description: The Application Servers Security Group ID. + Value: !GetAtt ServersStacks.Outputs.ServerSecurityGroupID + Condition: DeployServers \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network-master.yaml b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network-master.yaml new file mode 100755 index 00000000..782f72dc --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network-master.yaml @@ -0,0 +1,847 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Global Network and Core Network with 3 segments, basic policy and a Security VPC with Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, Gateway Load Balancer Endpoints and NAT Gateways for each AZ, in a new VPC for Cloud WAN (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - CloudWANSubnet1CIDR + - CloudWANSubnet2CIDR + - CloudWANSubnet3CIDR + - CloudWANSubnet4CIDR + - NatGwSubnet1CIDR + - NatGwSubnet2CIDR + - NatGwSubnet3CIDR + - NatGwSubnet4CIDR + - GWLBeSubnet1CIDR + - GWLBeSubnet2CIDR + - GWLBeSubnet3CIDR + - GWLBeSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - CloudWatch + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PublicSubnet3CIDR: + default: Public subnet 3 CIDR + PublicSubnet4CIDR: + default: Public subnet 4 CIDR + CloudWANSubnet1CIDR: + default: Cloud WAN subnet 1 CIDR + CloudWANSubnet2CIDR: + default: Cloud WAN subnet 2 CIDR + CloudWANSubnet3CIDR: + default: Cloud WAN subnet 3 CIDR + CloudWANSubnet4CIDR: + default: Cloud WAN subnet 4 CIDR + NatGwSubnet1CIDR: + default: NAT subnet 1 CIDR + NatGwSubnet2CIDR: + default: NAT subnet 2 CIDR + NatGwSubnet3CIDR: + default: NAT subnet 3 CIDR + NatGwSubnet4CIDR: + default: NAT subnet 4 CIDR + GWLBeSubnet1CIDR: + default: Gateway Load Balancer Endpoint subnet 1 CIDR + GWLBeSubnet2CIDR: + default: Gateway Load Balancer Endpoint subnet 2 CIDR + GWLBeSubnet3CIDR: + default: Gateway Load Balancer Endpoint subnet 3 CIDR + GWLBeSubnet4CIDR: + default: Gateway Load Balancer Endpoint subnet 4 CIDR + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + CloudWatch: + default: CloudWatch metrics + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved) + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + VPCCIDR: + Description: The CIDR block of the provided VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet3CIDR: + Description: CIDR block for public subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet4CIDR: + Description: CIDR block for public subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet1CIDR: + Description: CIDR block for Cloud WAN subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.12.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet2CIDR: + Description: CIDR block for Cloud WAN subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.22.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet3CIDR: + Description: CIDR block for Cloud WAN subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.32.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet4CIDR: + Description: CIDR block for Cloud WAN subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.42.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet1CIDR: + Description: CIDR block for NAT subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.13.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet2CIDR: + Description: CIDR block for NAT subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.23.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet3CIDR: + Description: CIDR block for NAT subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.33.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet4CIDR: + Description: CIDR block for NAT subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.43.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet1CIDR: + Description: CIDR block for GWLBe subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.14.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet2CIDR: + Description: CIDR block for GWLBe subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.24.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet3CIDR: + Description: CIDR block for GWLBe subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.34.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet4CIDR: + Description: CIDR block for GWLBe subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.44.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration + Type: String + Default: gwlb-wan-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration + Type: String + Default: gwlb-wan-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: gwlb-wan1 + ConstraintDescription: Must be a valid GWLB Name + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: tg-gwlb-wan1 + ConstraintDescription: Must be a valid target group name + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address + Type: String + Default: private + AllowedValues: + - private + - public + CloudWatch: + Description: Report Check Point specific CloudWatch metrics + Type: String + Default: false + AllowedValues: + - true + - false + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The license to install on the Security Management Server + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PublicSubnet3CIDR: !Ref PublicSubnet3CIDR + PublicSubnet4CIDR: !Ref PublicSubnet4CIDR + CreatePrivateSubnets: false + CreateAttachmentSubnets: true + AttachmentSubnet1CIDR: !Ref CloudWANSubnet1CIDR + AttachmentSubnet2CIDR: !Ref CloudWANSubnet2CIDR + AttachmentSubnet3CIDR: !Ref CloudWANSubnet3CIDR + AttachmentSubnet4CIDR: !Ref CloudWANSubnet4CIDR + CloudWANGwlbStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/gwlb-wan-global-network.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + IGWID: !GetAtt VPCStack.Outputs.IGWID + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + GatewaysSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.PublicSubnet1ID + - !GetAtt VPCStack.Outputs.PublicSubnet2ID + - !If [3AZs, !GetAtt VPCStack.Outputs.PublicSubnet3ID, !Ref 'AWS::NoValue'] + - !If [4AZs, !GetAtt VPCStack.Outputs.PublicSubnet4ID, !Ref 'AWS::NoValue'] + CloudWANSubnet1Id: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + CloudWANSubnet2Id: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + CloudWANSubnet3Id: !If [3AZs, !GetAtt VPCStack.Outputs.AttachmentSubnet3ID, ""] + CloudWANSubnet4Id: !If [4AZs, !GetAtt VPCStack.Outputs.AttachmentSubnet4ID, ""] + NatGwSubnet1CIDR: !Ref NatGwSubnet1CIDR + NatGwSubnet2CIDR: !Ref NatGwSubnet2CIDR + NatGwSubnet3CIDR: !Ref NatGwSubnet3CIDR + NatGwSubnet4CIDR: !Ref NatGwSubnet4CIDR + GWLBeSubnet1CIDR: !Ref GWLBeSubnet1CIDR + GWLBeSubnet2CIDR: !Ref GWLBeSubnet2CIDR + GWLBeSubnet3CIDR: !Ref GWLBeSubnet3CIDR + GWLBeSubnet4CIDR: !Ref GWLBeSubnet4CIDR + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + AllowUploadDownload: !Ref AllowUploadDownload + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + AdminEmail: !Ref AdminEmail + Shell: !Ref Shell + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + CloudWatch: !Ref CloudWatch + GWLBName: !Ref GWLBName + TargetGroupName: !Ref TargetGroupName + CrossZoneLoadBalancing: !Ref CrossZoneLoadBalancing + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + GatewaysPolicy: !Ref GatewaysPolicy + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses +Outputs: + VPCID: + Description: VPC ID + Value: !GetAtt VPCStack.Outputs.VPCID + ManagementPublicAddress: + Description: The public address of the management server + Value: !GetAtt CloudWANGwlbStack.Outputs.ManagementPublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name + Value: !GetAtt CloudWANGwlbStack.Outputs.ConfigurationTemplateName + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name + Value: !GetAtt CloudWANGwlbStack.Outputs.ControllerName + GWLBName: + Description: Gateway Load Balancer Name + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name + Value: !GetAtt CloudWANGwlbStack.Outputs.GWLBServiceName + CloudWANSubnet1ID: + Description: Cloud WAN subnet 1 ID in Availability Zone 1 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + CloudWANSubnet2ID: + Description: Cloud WAN subnet 2 ID in Availability Zone 2 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + CloudWANSubnet3ID: + Description: Cloud WAN subnet 3 ID in Availability Zone 3 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet3ID + Condition: 3AZs + CloudWANSubnet4ID: + Description: Cloud WAN subnet 4 ID in Availability Zone 4 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet4ID + Condition: 4AZs + CloudWANSubnet1CIDR: + Description: Cloud WAN subnet 1 CIDR in Availability Zone 1 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet1CIDR + CloudWANSubnet2CIDR: + Description: Cloud WAN subnet 2 CIDR in Availability Zone 2 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet2CIDR + CloudWANSubnet3CIDR: + Description: Cloud WAN subnet 3 CIDR in Availability Zone 3 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet3CIDR + Condition: 3AZs + CloudWANSubnet4CIDR: + Description: Cloud WAN subnet 4 CIDR in Availability Zone 4 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet4CIDR + Condition: 4AZs + GlobalNetworkId: + Description: Cloud WAN Global Network ID + Value: !GetAtt CloudWANGwlbStack.Outputs.GlobalNetworkId + CoreNetworkId: + Description: Cloud WAN Core Network ID + Value: !GetAtt CloudWANGwlbStack.Outputs.CoreNetworkId + SecurityVpcAttachmentId: + Description: Cloud WAN Security VPC Attachment ID + Value: !GetAtt CloudWANGwlbStack.Outputs.SecurityVpcAttachmentId \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network.yaml b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network.yaml new file mode 100755 index 00000000..b72ce09c --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-global-network.yaml @@ -0,0 +1,1317 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Global Network and Core Network with 3 segments, basic policy and a Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, Gateway Load Balancer Endpoints and NAT Gateways for each AZ, in an existing VPC for Cloud WAN (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - IGWID + - AvailabilityZones + - NumberOfAZs + - GatewaysSubnets + - CloudWANSubnet1Id + - CloudWANSubnet2Id + - CloudWANSubnet3Id + - CloudWANSubnet4Id + - NatGwSubnet1CIDR + - NatGwSubnet2CIDR + - NatGwSubnet3CIDR + - NatGwSubnet4CIDR + - GWLBeSubnet1CIDR + - GWLBeSubnet2CIDR + - GWLBeSubnet3CIDR + - GWLBeSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - CloudWatch + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + VPC: + default: VPC + IGWID: + default: Internet Gateway ID + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + GatewaysSubnets: + default: Gateways subnets + CloudWANSubnet1Id: + default: Cloud WAN Attachment subnet 1 Id + CloudWANSubnet2Id: + default: Cloud WAN Attachment subnet 2 Id + CloudWANSubnet3Id: + default: Cloud WAN Attachment subnet 3 Id + CloudWANSubnet4Id: + default: Cloud WAN Attachment subnet 4 Id + NatGwSubnet1CIDR: + default: NAT subnet 1 CIDR + NatGwSubnet2CIDR: + default: NAT subnet 2 CIDR + NatGwSubnet3CIDR: + default: NAT subnet 3 CIDR + NatGwSubnet4CIDR: + default: NAT subnet 4 CIDR + GWLBeSubnet1CIDR: + default: Gateway Load Balancer Endpoint subnet 1 CIDR + GWLBeSubnet2CIDR: + default: Gateway Load Balancer Endpoint subnet 2 CIDR + GWLBeSubnet3CIDR: + default: Gateway Load Balancer Endpoint subnet 3 CIDR + GWLBeSubnet4CIDR: + default: Gateway Load Balancer Endpoint subnet 4 CIDR + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + CloudWatch: + default: CloudWatch metrics + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + VPC: + Description: Select an existing VPC + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: You must select a VPC + IGWID: + Description: VPC's Internet Gateway Id (e.g. igw-123a4567) + Type: String + MinLength: 1 + ConstraintDescription: You must insert an Internet Gateway Id + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved) + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + GatewaysSubnets: + Description: Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet + Type: List + MinLength: 2 + CloudWANSubnet1Id: + Description: The Cloud WAN attachment subnet ID located in the 1st Availability Zone + Type: String + MinLength: 1 + ConstraintDescription: You must insert Cloud WAN Subnet Id for Availability Zone 1 + CloudWANSubnet2Id: + Description: The Cloud WAN attachment subnet ID located in the 2nd Availability Zone + Type: String + MinLength: 1 + ConstraintDescription: You must insert Cloud WAN Subnet Id for Availability Zone 2 + CloudWANSubnet3Id: + Description: The Cloud WAN attachment subnet ID located in the 3rd Availability Zone + Type: String + CloudWANSubnet4Id: + Description: The Cloud WAN attachment subnet ID located in the 4th Availability Zone + Type: String + NatGwSubnet1CIDR: + Description: CIDR block for NAT subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.13.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet2CIDR: + Description: CIDR block for NAT subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.23.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet3CIDR: + Description: CIDR block for NAT subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.33.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet4CIDR: + Description: CIDR block for NAT subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.43.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet1CIDR: + Description: CIDR block for GWLBe subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.14.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet2CIDR: + Description: CIDR block for GWLBe subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.24.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet3CIDR: + Description: CIDR block for GWLBe subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.34.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet4CIDR: + Description: CIDR block for GWLBe subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.44.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration + Type: String + Default: gwlb-wan-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration + Type: String + Default: gwlb-wan-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayName: + Description: The name tag of the Security Gateway instances (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address + Type: String + Default: private + AllowedValues: + - private + - public + CloudWatch: + Description: Report Check Point specific CloudWatch metrics + Type: String + Default: false + AllowedValues: + - true + - false + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: gwlb-wan1 + ConstraintDescription: Must be a valid GWLB Name + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: tg-gwlb-wan1 + ConstraintDescription: Must be a valid target group name + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The license to install on the Security Management Server + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] +Resources: + GWLBeSubnet1: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 1 + - Key: Network + Value: Private + GWLBeSubnet2: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 2 + - Key: Network + Value: Private + GWLBeSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 3 + - Key: Network + Value: Private + GWLBeSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 4 + - Key: Network + Value: Private + GWLBeSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 1 Route Table + - Key: Network + Value: Private + GWLBeSubnet1NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway1 + RouteTableId: !Ref GWLBeSubnet1RouteTable + GWLBeSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref GWLBeSubnet1RouteTable + SubnetId: !Ref GWLBeSubnet1 + GWLBeSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 2 Route Table + - Key: Network + Value: Private + GWLBeSubnet2NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway2 + RouteTableId: !Ref GWLBeSubnet2RouteTable + GWLBeSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref GWLBeSubnet2RouteTable + SubnetId: !Ref GWLBeSubnet2 + GWLBeSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 3 Route Table + - Key: Network + Value: Private + GWLBeSubnet3NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway3 + RouteTableId: !Ref GWLBeSubnet3RouteTable + GWLBeSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref GWLBeSubnet3RouteTable + SubnetId: !Ref GWLBeSubnet3 + GWLBeSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 4 Route Table + - Key: Network + Value: Private + GWLBeSubnet4NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway4 + RouteTableId: !Ref GWLBeSubnet4RouteTable + GWLBeSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref GWLBeSubnet4RouteTable + SubnetId: !Ref GWLBeSubnet4 + NatGwSubnet1: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 1 + - Key: Network + Value: Private + NatGwSubnet2: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 2 + - Key: Network + Value: Private + NatGwSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 3 + - Key: Network + Value: Private + NatGwSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 4 + - Key: Network + Value: Private + NatGwSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 1 Route Table + - Key: Network + Value: Public + NatGwSubnet1NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet1RouteTable + NatGwSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref NatGwSubnet1RouteTable + SubnetId: !Ref NatGwSubnet1 + NatGwSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 2 Route Table + - Key: Network + Value: Public + NatGwSubnet2NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet2RouteTable + NatGwSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref NatGwSubnet2RouteTable + SubnetId: !Ref NatGwSubnet2 + NatGwSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 3 Route Table + - Key: Network + Value: Public + NatGwSubnet3NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet3RouteTable + NatGwSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref NatGwSubnet3RouteTable + SubnetId: !Ref NatGwSubnet3 + NatGwSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 4 Route Table + - Key: Network + Value: Public + NatGwSubnet4NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet4RouteTable + NatGwSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref NatGwSubnet4RouteTable + SubnetId: !Ref NatGwSubnet4 + GWLBStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/gwlb.yaml + Parameters: + VPC: !Ref VPC + GatewaysSubnets: !Join [',', !Ref GatewaysSubnets] + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + AllowUploadDownload: !Ref AllowUploadDownload + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + AdminEmail: !Ref AdminEmail + Shell: !Ref Shell + GWLBName: !Ref GWLBName + TargetGroupName: !Ref TargetGroupName + AcceptConnectionRequired: false + CrossZoneLoadBalancing: !Ref CrossZoneLoadBalancing + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Join + - ';' + - - 'echo -e "\nStarting Bootstrap script\n"' + - 'echo "Adding cloud wan identifier to cloud-version"' + - 'template="autoscale_gwlb_cloud_wan"' + - 'cv_path="/etc/cloud-version"' + - 'if test -f ${cv_path}; then sed -i ''/template_name/c\template_name: ''"${template}"'''' /etc/cloud-version; fi' + - 'cv_json_path="/etc/cloud-version.json"' + - 'cv_json_path_tmp="/etc/cloud-version-tmp.json"' + - 'if test -f ${cv_json_path}; then cat ${cv_json_path} | jq ''.template_name = "''"${template}"''"'' > ${cv_json_path_tmp}; mv ${cv_json_path_tmp} ${cv_json_path}; fi' + - 'echo -e "\nFinished Bootstrap script\n"' + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + GatewaysPolicy: !Ref GatewaysPolicy + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + GWLBe1: + DependsOn: [GWLBStack, GWLBeSubnet1] + Type: AWS::EC2::VPCEndpoint + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet1 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe2: + DependsOn: [GWLBStack, GWLBeSubnet2] + Type: AWS::EC2::VPCEndpoint + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet2 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe3: + DependsOn: [GWLBStack, GWLBeSubnet3] + Type: AWS::EC2::VPCEndpoint + Condition: 3AZs + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet3 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe4: + DependsOn: [GWLBStack, GWLBeSubnet4] + Type: AWS::EC2::VPCEndpoint + Condition: 4AZs + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet4 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + CloudWANAttachmentSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 1 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet1GWLBeDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe1 + RouteTableId: !Ref CloudWANAttachmentSubnet1RouteTable + CloudWANAttachmentSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet1RouteTable + SubnetId: !Ref CloudWANSubnet1Id + CloudWANAttachmentSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 2 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet2GWLBeDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe2 + RouteTableId: !Ref CloudWANAttachmentSubnet2RouteTable + CloudWANAttachmentSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet2RouteTable + SubnetId: !Ref CloudWANSubnet2Id + CloudWANAttachmentSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 3 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet3GWLBeDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe3 + RouteTableId: !Ref CloudWANAttachmentSubnet3RouteTable + CloudWANAttachmentSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet3RouteTable + SubnetId: !Ref CloudWANSubnet3Id + CloudWANAttachmentSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 4 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet4GWLBeDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe4 + RouteTableId: !Ref CloudWANAttachmentSubnet4RouteTable + CloudWANAttachmentSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet4RouteTable + SubnetId: !Ref CloudWANSubnet4Id + CloudWANGlobalNetwork: + Type: AWS::NetworkManager::GlobalNetwork + Properties: + Description: Check Point Gateway Load Balancer for Cloud WAN Global Network + CloudWANCoreNetwork: + Type: AWS::NetworkManager::CoreNetwork + Properties: + Description: Check Point Gateway Load Balancer for Cloud WAN Core Network + GlobalNetworkId: !Ref CloudWANGlobalNetwork + PolicyDocument: + { + "version": "2021.12", + "core-network-configuration": { + "vpn-ecmp-support": false, + "asn-ranges": [ + "64512-65534" + ], + "edge-locations": [ + { + "location": { "Ref" : "AWS::Region" } + } + ] + }, + "segments": [ + { + "name": "dev", + "edge-locations": [{ "Ref" : "AWS::Region" }], + "require-attachment-acceptance": false + }, + { + "name": "SecurityVpc", + "edge-locations": [{ "Ref" : "AWS::Region" }], + "require-attachment-acceptance": false + }, + { + "name": "prod", + "edge-locations": [{ "Ref" : "AWS::Region" }], + "require-attachment-acceptance": false + } + ], + "segment-actions": [ + { + "action": "share", + "mode": "attachment-route", + "segment": "SecurityVpc", + "share-with": [ + "dev", + "prod" + ] + } + ], + "attachment-policies": [ + { + "rule-number": 100, + "conditions": [ + { + "type": "tag-value", + "operator": "equals", + "key": "segment", + "value": "dev" + } + ], + "action": { + "association-method": "constant", + "segment": "dev" + } + }, + { + "rule-number": 150, + "conditions": [ + { + "type": "tag-value", + "operator": "equals", + "key": "segment", + "value": "prod" + } + ], + "action": { + "association-method": "constant", + "segment": "prod" + } + }, + { + "rule-number": 200, + "conditions": [ + { + "type": "tag-value", + "operator": "equals", + "key": "segment", + "value": "SecurityVpc" + } + ], + "action": { + "association-method": "constant", + "segment": "SecurityVpc" + } + } + ] + } + CloudWANSecurityVpcAttachement: + DependsOn: CloudWANCoreNetwork + Type: AWS::NetworkManager::VpcAttachment + Properties: + CoreNetworkId: !GetAtt CloudWANCoreNetwork.CoreNetworkId + SubnetArns: + - !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet1Id ] ] + - !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet2Id ] ] + - !If [ 3AZs, !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet3Id ] ] , !Ref 'AWS::NoValue' ] + - !If [ 4AZs, !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet4Id ] ] , !Ref 'AWS::NoValue' ] + Tags: + - Key: segment + Value: SecurityVpc + VpcArn: !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":vpc/", !Ref VPC ] ] + NatGwPublicAddress1: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + NatGwPublicAddress2: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + NatGwPublicAddress3: + Type: AWS::EC2::EIP + Condition: 3AZs + Properties: + Domain: vpc + NatGwPublicAddress4: + Type: AWS::EC2::EIP + Condition: 4AZs + Properties: + Domain: vpc + NatGateway1: + DependsOn: [GWLBStack, NatGwSubnet1] + Type: AWS::EC2::NatGateway + Properties: + AllocationId: !GetAtt NatGwPublicAddress1.AllocationId + SubnetId: !Ref NatGwSubnet1 + Tags: + - Key: Name + Value: NatGW1 + NatGateway2: + DependsOn: [GWLBStack, NatGwSubnet2] + Type: AWS::EC2::NatGateway + Properties: + AllocationId: !GetAtt NatGwPublicAddress2.AllocationId + SubnetId: !Ref NatGwSubnet2 + Tags: + - Key: Name + Value: NatGW2 + NatGateway3: + DependsOn: [GWLBStack, NatGwSubnet3] + Type: AWS::EC2::NatGateway + Condition: 3AZs + Properties: + AllocationId: !GetAtt NatGwPublicAddress3.AllocationId + SubnetId: !Ref NatGwSubnet3 + Tags: + - Key: Name + Value: NatGW3 + NatGateway4: + DependsOn: [GWLBStack, NatGwSubnet4] + Type: AWS::EC2::NatGateway + Condition: 4AZs + Properties: + AllocationId: !GetAtt NatGwPublicAddress4.AllocationId + SubnetId: !Ref NatGwSubnet4 + Tags: + - Key: Name + Value: NatGW4 +Outputs: + ManagementPublicAddress: + Description: The public address of the management server + Value: !GetAtt GWLBStack.Outputs.ManagementPublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name + Value: !GetAtt GWLBStack.Outputs.ConfigurationTemplateName + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name + Value: !GetAtt GWLBStack.Outputs.ControllerName + GWLBName: + Description: Gateway Load Balancer Name + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name + Value: !GetAtt GWLBStack.Outputs.GWLBServiceName + GlobalNetworkId: + Description: Cloud WAN Global Network ID + Value: !GetAtt CloudWANGlobalNetwork.Id + CoreNetworkId: + Description: Cloud WAN Core Network ID + Value: !GetAtt CloudWANCoreNetwork.CoreNetworkId + SecurityVpcAttachmentId: + Description: Cloud WAN Security VPC Attachment ID + Value: !GetAtt CloudWANSecurityVpcAttachement.AttachmentId \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc-master.yaml b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc-master.yaml new file mode 100755 index 00000000..b9d86c06 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc-master.yaml @@ -0,0 +1,874 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, Gateway Load Balancer Endpoints and NAT Gateways for each AZ, in a new VPC for Cloud WAN and attach the VPC to existing Core Network (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - CloudWANSubnet1CIDR + - CloudWANSubnet2CIDR + - CloudWANSubnet3CIDR + - CloudWANSubnet4CIDR + - NatGwSubnet1CIDR + - NatGwSubnet2CIDR + - NatGwSubnet3CIDR + - NatGwSubnet4CIDR + - GWLBeSubnet1CIDR + - GWLBeSubnet2CIDR + - GWLBeSubnet3CIDR + - GWLBeSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - CloudWatch + - Label: + default: Cloud WAN configuration + Parameters: + - CoreNetworkID + - VPCAttachmentTagKey + - VPCAttachmentTagValue + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PublicSubnet3CIDR: + default: Public subnet 3 CIDR + PublicSubnet4CIDR: + default: Public subnet 4 CIDR + CloudWANSubnet1CIDR: + default: Cloud WAN subnet 1 CIDR + CloudWANSubnet2CIDR: + default: Cloud WAN subnet 2 CIDR + CloudWANSubnet3CIDR: + default: Cloud WAN subnet 3 CIDR + CloudWANSubnet4CIDR: + default: Cloud WAN subnet 4 CIDR + NatGwSubnet1CIDR: + default: NAT subnet 1 CIDR + NatGwSubnet2CIDR: + default: NAT subnet 2 CIDR + NatGwSubnet3CIDR: + default: NAT subnet 3 CIDR + NatGwSubnet4CIDR: + default: NAT subnet 4 CIDR + GWLBeSubnet1CIDR: + default: Gateway Load Balancer Endpoint subnet 1 CIDR + GWLBeSubnet2CIDR: + default: Gateway Load Balancer Endpoint subnet 2 CIDR + GWLBeSubnet3CIDR: + default: Gateway Load Balancer Endpoint subnet 3 CIDR + GWLBeSubnet4CIDR: + default: Gateway Load Balancer Endpoint subnet 4 CIDR + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + CloudWatch: + default: CloudWatch metrics + CoreNetworkID: + default: Cloud WAN Core Network ID + VPCAttachmentTagKey: + default: Cloud WAN VPC attachment tag key + VPCAttachmentTagValue: + default: Cloud WAN VPC attachment tag value + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved) + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + VPCCIDR: + Description: The CIDR block of the provided VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet3CIDR: + Description: CIDR block for public subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + PublicSubnet4CIDR: + Description: CIDR block for public subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet1CIDR: + Description: CIDR block for Cloud WAN subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.12.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet2CIDR: + Description: CIDR block for Cloud WAN subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.22.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet3CIDR: + Description: CIDR block for Cloud WAN subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.32.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + CloudWANSubnet4CIDR: + Description: CIDR block for Cloud WAN subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.42.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet1CIDR: + Description: CIDR block for NAT subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.13.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet2CIDR: + Description: CIDR block for NAT subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.23.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet3CIDR: + Description: CIDR block for NAT subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.33.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet4CIDR: + Description: CIDR block for NAT subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.43.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet1CIDR: + Description: CIDR block for GWLBe subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.14.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet2CIDR: + Description: CIDR block for GWLBe subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.24.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet3CIDR: + Description: CIDR block for GWLBe subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.34.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet4CIDR: + Description: CIDR block for GWLBe subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.44.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration + Type: String + Default: gwlb-wan-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration + Type: String + Default: gwlb-wan-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: gwlb-wan1 + ConstraintDescription: Must be a valid GWLB Name + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: tg-gwlb-wan1 + ConstraintDescription: Must be a valid target group name + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address + Type: String + Default: private + AllowedValues: + - private + - public + CloudWatch: + Description: Report Check Point specific CloudWatch metrics + Type: String + Default: false + AllowedValues: + - true + - false + CoreNetworkID: + Description: The Core Network ID to attach the Security VPC with + Type: String + MinLength: 1 + ConstraintDescription: You must insert a Core Network ID + VPCAttachmentTagKey: + Description: The tag key of the Security VPC attachment to Cloud WAN Core Newtork + Type: String + MinLength: 1 + Default: Check-Point-Cloud-WAN + VPCAttachmentTagValue: + Description: The tag value of the Security VPC attachment to Cloud WAN Core Newtork + Type: String + MinLength: 1 + Default: Security-VPC-Attachment + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The license to install on the Security Management Server + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PublicSubnet3CIDR: !Ref PublicSubnet3CIDR + PublicSubnet4CIDR: !Ref PublicSubnet4CIDR + CreatePrivateSubnets: false + CreateAttachmentSubnets: true + AttachmentSubnet1CIDR: !Ref CloudWANSubnet1CIDR + AttachmentSubnet2CIDR: !Ref CloudWANSubnet2CIDR + AttachmentSubnet3CIDR: !Ref CloudWANSubnet3CIDR + AttachmentSubnet4CIDR: !Ref CloudWANSubnet4CIDR + CloudWANGwlbStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/gwlb-wan-security-vpc.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + IGWID: !GetAtt VPCStack.Outputs.IGWID + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + GatewaysSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.PublicSubnet1ID + - !GetAtt VPCStack.Outputs.PublicSubnet2ID + - !If [3AZs, !GetAtt VPCStack.Outputs.PublicSubnet3ID, !Ref 'AWS::NoValue'] + - !If [4AZs, !GetAtt VPCStack.Outputs.PublicSubnet4ID, !Ref 'AWS::NoValue'] + CloudWANSubnet1Id: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + CloudWANSubnet2Id: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + CloudWANSubnet3Id: !If [3AZs, !GetAtt VPCStack.Outputs.AttachmentSubnet3ID, ""] + CloudWANSubnet4Id: !If [4AZs, !GetAtt VPCStack.Outputs.AttachmentSubnet4ID, ""] + NatGwSubnet1CIDR: !Ref NatGwSubnet1CIDR + NatGwSubnet2CIDR: !Ref NatGwSubnet2CIDR + NatGwSubnet3CIDR: !Ref NatGwSubnet3CIDR + NatGwSubnet4CIDR: !Ref NatGwSubnet4CIDR + GWLBeSubnet1CIDR: !Ref GWLBeSubnet1CIDR + GWLBeSubnet2CIDR: !Ref GWLBeSubnet2CIDR + GWLBeSubnet3CIDR: !Ref GWLBeSubnet3CIDR + GWLBeSubnet4CIDR: !Ref GWLBeSubnet4CIDR + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + AllowUploadDownload: !Ref AllowUploadDownload + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + AdminEmail: !Ref AdminEmail + Shell: !Ref Shell + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + CloudWatch: !Ref CloudWatch + CoreNetworkID: !Ref CoreNetworkID + VPCAttachmentTagKey: !Ref VPCAttachmentTagKey + VPCAttachmentTagValue: !Ref VPCAttachmentTagValue + GWLBName: !Ref GWLBName + TargetGroupName: !Ref TargetGroupName + CrossZoneLoadBalancing: !Ref CrossZoneLoadBalancing + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + GatewaysPolicy: !Ref GatewaysPolicy + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses +Outputs: + VPCID: + Description: VPC ID + Value: !GetAtt VPCStack.Outputs.VPCID + ManagementPublicAddress: + Description: The public address of the management server + Value: !GetAtt CloudWANGwlbStack.Outputs.ManagementPublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name + Value: !GetAtt CloudWANGwlbStack.Outputs.ConfigurationTemplateName + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name + Value: !GetAtt CloudWANGwlbStack.Outputs.ControllerName + GWLBName: + Description: Gateway Load Balancer Name + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name + Value: !GetAtt CloudWANGwlbStack.Outputs.GWLBServiceName + CloudWANSubnet1ID: + Description: Cloud WAN subnet 1 ID in Availability Zone 1 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + CloudWANSubnet2ID: + Description: Cloud WAN subnet 2 ID in Availability Zone 2 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + CloudWANSubnet3ID: + Description: Cloud WAN subnet 3 ID in Availability Zone 3 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet3ID + Condition: 3AZs + CloudWANSubnet4ID: + Description: Cloud WAN subnet 4 ID in Availability Zone 4 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet4ID + Condition: 4AZs + CloudWANSubnet1CIDR: + Description: Cloud WAN subnet 1 CIDR in Availability Zone 1 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet1CIDR + CloudWANSubnet2CIDR: + Description: Cloud WAN subnet 2 CIDR in Availability Zone 2 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet2CIDR + CloudWANSubnet3CIDR: + Description: Cloud WAN subnet 3 CIDR in Availability Zone 3 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet3CIDR + Condition: 3AZs + CloudWANSubnet4CIDR: + Description: Cloud WAN subnet 4 CIDR in Availability Zone 4 + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet4CIDR + Condition: 4AZs + SecurityVpcAttachmentId: + Description: Cloud WAN Security VPC Attachment ID + Value: !GetAtt CloudWANGwlbStack.Outputs.SecurityVpcAttachmentId + SecurityVpcAttachmentSegment: + Description: Cloud WAN Security VPC Attachment Segment + Value: !GetAtt CloudWANGwlbStack.Outputs.SecurityVpcAttachmentSegment \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc.yaml b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc.yaml new file mode 100755 index 00000000..cb188c84 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/gwlb-wan-security-vpc.yaml @@ -0,0 +1,1241 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, Gateway Load Balancer Endpoints and NAT Gateways for each AZ, in an existing VPC for Cloud WAN and attach the VPC to existing Core Network (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - IGWID + - AvailabilityZones + - NumberOfAZs + - GatewaysSubnets + - CloudWANSubnet1Id + - CloudWANSubnet2Id + - CloudWANSubnet3Id + - CloudWANSubnet4Id + - NatGwSubnet1CIDR + - NatGwSubnet2CIDR + - NatGwSubnet3CIDR + - NatGwSubnet4CIDR + - GWLBeSubnet1CIDR + - GWLBeSubnet2CIDR + - GWLBeSubnet3CIDR + - GWLBeSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - CloudWatch + - Label: + default: Cloud WAN configuration + Parameters: + - CoreNetworkID + - VPCAttachmentTagKey + - VPCAttachmentTagValue + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + VPC: + default: VPC + IGWID: + default: Internet Gateway ID + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + GatewaysSubnets: + default: Gateways subnets + CloudWANSubnet1Id: + default: Cloud WAN Attachment subnet 1 Id + CloudWANSubnet2Id: + default: Cloud WAN Attachment subnet 2 Id + CloudWANSubnet3Id: + default: Cloud WAN Attachment subnet 3 Id + CloudWANSubnet4Id: + default: Cloud WAN Attachment subnet 4 Id + NatGwSubnet1CIDR: + default: NAT subnet 1 CIDR + NatGwSubnet2CIDR: + default: NAT subnet 2 CIDR + NatGwSubnet3CIDR: + default: NAT subnet 3 CIDR + NatGwSubnet4CIDR: + default: NAT subnet 4 CIDR + GWLBeSubnet1CIDR: + default: Gateway Load Balancer Endpoint subnet 1 CIDR + GWLBeSubnet2CIDR: + default: Gateway Load Balancer Endpoint subnet 2 CIDR + GWLBeSubnet3CIDR: + default: Gateway Load Balancer Endpoint subnet 3 CIDR + GWLBeSubnet4CIDR: + default: Gateway Load Balancer Endpoint subnet 4 CIDR + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + CloudWatch: + default: CloudWatch metrics + CoreNetworkID: + default: Cloud WAN Core Network ID + VPCAttachmentTagKey: + default: Cloud WAN VPC attachment tag key + VPCAttachmentTagValue: + default: Cloud WAN VPC attachment tag value + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + VPC: + Description: Select an existing VPC + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: You must select a VPC + IGWID: + Description: VPC's Internet Gateway Id (e.g. igw-123a4567) + Type: String + MinLength: 1 + ConstraintDescription: You must insert an Internet Gateway Id + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved) + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + GatewaysSubnets: + Description: Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet + Type: List + MinLength: 2 + CloudWANSubnet1Id: + Description: The Cloud WAN attachment subnet ID located in the 1st Availability Zone + Type: String + MinLength: 1 + ConstraintDescription: You must insert Cloud WAN Subnet Id for Availability Zone 1 + CloudWANSubnet2Id: + Description: The Cloud WAN attachment subnet ID located in the 2nd Availability Zone + Type: String + MinLength: 1 + ConstraintDescription: You must insert Cloud WAN Subnet Id for Availability Zone 2 + CloudWANSubnet3Id: + Description: The Cloud WAN attachment subnet ID located in the 3rd Availability Zone + Type: String + CloudWANSubnet4Id: + Description: The Cloud WAN attachment subnet ID located in the 4th Availability Zone + Type: String + NatGwSubnet1CIDR: + Description: CIDR block for NAT subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.13.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet2CIDR: + Description: CIDR block for NAT subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.23.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet3CIDR: + Description: CIDR block for NAT subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.33.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + NatGwSubnet4CIDR: + Description: CIDR block for NAT subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.43.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet1CIDR: + Description: CIDR block for GWLBe subnet 1 located in the 1st Availability Zone + Type: String + Default: 10.0.14.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet2CIDR: + Description: CIDR block for GWLBe subnet 2 located in the 2nd Availability Zone + Type: String + Default: 10.0.24.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet3CIDR: + Description: CIDR block for GWLBe subnet 3 located in the 3rd Availability Zone + Type: String + Default: 10.0.34.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + GWLBeSubnet4CIDR: + Description: CIDR block for GWLBe subnet 4 located in the 4th Availability Zone + Type: String + Default: 10.0.44.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28 + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration + Type: String + Default: gwlb-wan-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration + Type: String + Default: gwlb-wan-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayName: + Description: The name tag of the Security Gateway instances (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address + Type: String + Default: private + AllowedValues: + - private + - public + CloudWatch: + Description: Report Check Point specific CloudWatch metrics + Type: String + Default: false + AllowedValues: + - true + - false + CoreNetworkID: + Description: The Core Network ID to attach the Security VPC with + Type: String + MinLength: 1 + ConstraintDescription: You must insert a Core Network ID + VPCAttachmentTagKey: + Description: The tag key of the Security VPC attachment to Cloud WAN Core Newtork + Type: String + MinLength: 1 + Default: Check-Point-Cloud-WAN + VPCAttachmentTagValue: + Description: The tag value of the Security VPC attachment to Cloud WAN Core Newtork + Type: String + MinLength: 1 + Default: Security-VPC-Attachment + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: gwlb-wan1 + ConstraintDescription: Must be a valid GWLB Name + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: tg-gwlb-wan1 + ConstraintDescription: Must be a valid target group name + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The license to install on the Security Management Server + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] +Resources: + GWLBeSubnet1: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 1 + - Key: Network + Value: Private + GWLBeSubnet2: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 2 + - Key: Network + Value: Private + GWLBeSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 3 + - Key: Network + Value: Private + GWLBeSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 4 + - Key: Network + Value: Private + GWLBeSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 1 Route Table + - Key: Network + Value: Private + GWLBeSubnet1NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway1 + RouteTableId: !Ref GWLBeSubnet1RouteTable + GWLBeSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref GWLBeSubnet1RouteTable + SubnetId: !Ref GWLBeSubnet1 + GWLBeSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 2 Route Table + - Key: Network + Value: Private + GWLBeSubnet2NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway2 + RouteTableId: !Ref GWLBeSubnet2RouteTable + GWLBeSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref GWLBeSubnet2RouteTable + SubnetId: !Ref GWLBeSubnet2 + GWLBeSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 3 Route Table + - Key: Network + Value: Private + GWLBeSubnet3NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway3 + RouteTableId: !Ref GWLBeSubnet3RouteTable + GWLBeSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref GWLBeSubnet3RouteTable + SubnetId: !Ref GWLBeSubnet3 + GWLBeSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 4 Route Table + - Key: Network + Value: Private + GWLBeSubnet4NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway4 + RouteTableId: !Ref GWLBeSubnet4RouteTable + GWLBeSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref GWLBeSubnet4RouteTable + SubnetId: !Ref GWLBeSubnet4 + NatGwSubnet1: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 1 + - Key: Network + Value: Private + NatGwSubnet2: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 2 + - Key: Network + Value: Private + NatGwSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 3 + - Key: Network + Value: Private + NatGwSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 4 + - Key: Network + Value: Private + NatGwSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 1 Route Table + - Key: Network + Value: Public + NatGwSubnet1NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet1RouteTable + NatGwSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref NatGwSubnet1RouteTable + SubnetId: !Ref NatGwSubnet1 + NatGwSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 2 Route Table + - Key: Network + Value: Public + NatGwSubnet2NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet2RouteTable + NatGwSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref NatGwSubnet2RouteTable + SubnetId: !Ref NatGwSubnet2 + NatGwSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 3 Route Table + - Key: Network + Value: Public + NatGwSubnet3NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet3RouteTable + NatGwSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref NatGwSubnet3RouteTable + SubnetId: !Ref NatGwSubnet3 + NatGwSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 4 Route Table + - Key: Network + Value: Public + NatGwSubnet4NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet4RouteTable + NatGwSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref NatGwSubnet4RouteTable + SubnetId: !Ref NatGwSubnet4 + GWLBStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/gwlb.yaml + Parameters: + VPC: !Ref VPC + GatewaysSubnets: !Join [',', !Ref GatewaysSubnets] + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + AllowUploadDownload: !Ref AllowUploadDownload + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + AdminEmail: !Ref AdminEmail + Shell: !Ref Shell + GWLBName: !Ref GWLBName + TargetGroupName: !Ref TargetGroupName + AcceptConnectionRequired: false + CrossZoneLoadBalancing: !Ref CrossZoneLoadBalancing + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Join + - ';' + - - 'echo -e "\nStarting Bootstrap script\n"' + - 'echo "Adding cloud wan identifier to cloud-version"' + - 'template="autoscale_gwlb_cloud_wan"' + - 'cv_path="/etc/cloud-version"' + - 'if test -f ${cv_path}; then sed -i ''/template_name/c\template_name: ''"${template}"'''' /etc/cloud-version; fi' + - 'cv_json_path="/etc/cloud-version.json"' + - 'cv_json_path_tmp="/etc/cloud-version-tmp.json"' + - 'if test -f ${cv_json_path}; then cat ${cv_json_path} | jq ''.template_name = "''"${template}"''"'' > ${cv_json_path_tmp}; mv ${cv_json_path_tmp} ${cv_json_path}; fi' + - 'echo -e "\nFinished Bootstrap script\n"' + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + GatewaysPolicy: !Ref GatewaysPolicy + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + GWLBe1: + DependsOn: [GWLBStack, GWLBeSubnet1] + Type: AWS::EC2::VPCEndpoint + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet1 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe2: + DependsOn: [GWLBStack, GWLBeSubnet2] + Type: AWS::EC2::VPCEndpoint + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet2 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe3: + DependsOn: [GWLBStack, GWLBeSubnet3] + Type: AWS::EC2::VPCEndpoint + Condition: 3AZs + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet3 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe4: + DependsOn: [GWLBStack, GWLBeSubnet4] + Type: AWS::EC2::VPCEndpoint + Condition: 4AZs + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet4 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + CloudWANAttachmentSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 1 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet1GWLBeDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe1 + RouteTableId: !Ref CloudWANAttachmentSubnet1RouteTable + CloudWANAttachmentSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet1RouteTable + SubnetId: !Ref CloudWANSubnet1Id + CloudWANAttachmentSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 2 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet2GWLBeDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe2 + RouteTableId: !Ref CloudWANAttachmentSubnet2RouteTable + CloudWANAttachmentSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet2RouteTable + SubnetId: !Ref CloudWANSubnet2Id + CloudWANAttachmentSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 3 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet3GWLBeDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe3 + RouteTableId: !Ref CloudWANAttachmentSubnet3RouteTable + CloudWANAttachmentSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet3RouteTable + SubnetId: !Ref CloudWANSubnet3Id + CloudWANAttachmentSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: CloudWAN Attachment Subnet 4 Route Table + - Key: Network + Value: Private + CloudWANAttachmentSubnet4GWLBeDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe4 + RouteTableId: !Ref CloudWANAttachmentSubnet4RouteTable + CloudWANAttachmentSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref CloudWANAttachmentSubnet4RouteTable + SubnetId: !Ref CloudWANSubnet4Id + CloudWANAttachement: + Type: AWS::NetworkManager::VpcAttachment + Properties: + CoreNetworkId: !Ref CoreNetworkID + SubnetArns: + - !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet1Id] ] + - !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet2Id] ] + - !If [3AZs, !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet3Id] ] , !Ref 'AWS::NoValue'] + - !If [4AZs, !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":subnet/", !Ref CloudWANSubnet4Id] ] , !Ref 'AWS::NoValue'] + Tags: + - Key: !Ref VPCAttachmentTagKey + Value: !Ref VPCAttachmentTagValue + VpcArn: !Join [ "", [ "arn:aws:ec2:", !Ref "AWS::Region", ":", !Ref "AWS::AccountId", ":vpc/", !Ref VPC] ] + NatGwPublicAddress1: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + NatGwPublicAddress2: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + NatGwPublicAddress3: + Type: AWS::EC2::EIP + Condition: 3AZs + Properties: + Domain: vpc + NatGwPublicAddress4: + Type: AWS::EC2::EIP + Condition: 4AZs + Properties: + Domain: vpc + NatGateway1: + DependsOn: [GWLBStack, NatGwSubnet1] + Type: AWS::EC2::NatGateway + Properties: + AllocationId: !GetAtt NatGwPublicAddress1.AllocationId + SubnetId: !Ref NatGwSubnet1 + Tags: + - Key: Name + Value: NatGW1 + NatGateway2: + DependsOn: [GWLBStack, NatGwSubnet2] + Type: AWS::EC2::NatGateway + Properties: + AllocationId: !GetAtt NatGwPublicAddress2.AllocationId + SubnetId: !Ref NatGwSubnet2 + Tags: + - Key: Name + Value: NatGW2 + NatGateway3: + DependsOn: [GWLBStack, NatGwSubnet3] + Type: AWS::EC2::NatGateway + Condition: 3AZs + Properties: + AllocationId: !GetAtt NatGwPublicAddress3.AllocationId + SubnetId: !Ref NatGwSubnet3 + Tags: + - Key: Name + Value: NatGW3 + NatGateway4: + DependsOn: [GWLBStack, NatGwSubnet4] + Type: AWS::EC2::NatGateway + Condition: 4AZs + Properties: + AllocationId: !GetAtt NatGwPublicAddress4.AllocationId + SubnetId: !Ref NatGwSubnet4 + Tags: + - Key: Name + Value: NatGW4 +Outputs: + ManagementPublicAddress: + Description: The public address of the management server + Value: !GetAtt GWLBStack.Outputs.ManagementPublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name + Value: !GetAtt GWLBStack.Outputs.ConfigurationTemplateName + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name + Value: !GetAtt GWLBStack.Outputs.ControllerName + GWLBName: + Description: Gateway Load Balancer Name + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name + Value: !GetAtt GWLBStack.Outputs.GWLBServiceName + SecurityVpcAttachmentId: + Description: Cloud WAN Security VPC Attachment ID + Value: !GetAtt CloudWANAttachement.AttachmentId + SecurityVpcAttachmentSegment: + Description: Cloud WAN Security VPC Attachment Segment + Value: !GetAtt CloudWANAttachement.SegmentName \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/gwlb/gwlb.yaml b/deprecated/aws/templates/R80.40/gwlb/gwlb.yaml new file mode 100755 index 00000000..4a590be4 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/gwlb.yaml @@ -0,0 +1,732 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Network Configuration + Parameters: + - VPC + - GatewaysSubnets + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - AcceptConnectionRequired + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - AllocatePublicAddress + - CloudWatch + - GatewayBootstrapScript + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + VPC: + default: VPC + GatewaysSubnets: + default: Gateways subnets + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + AcceptConnectionRequired: + default: Connection Acceptance Required + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + AllocatePublicAddress: + default: Allocate Public IPs + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Gateways bootstrap script + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: You must select a VPC. + GatewaysSubnets: + Description: Select at least 2 public subnets in the VPC. + Type: List + MinLength: 2 + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: gwlb-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: gwlb-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: gwlb1 + ConstraintDescription: Must be a valid GWLB Name. + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: tg1 + ConstraintDescription: Must be a valid target group name. + AcceptConnectionRequired: + Description: Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). + Default: "false" + AllowedValues: ["true", "false"] + Type: String + ConstraintDescription: Must be true or false. + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication acti.vation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + AllocatePublicAddress: + Description: Allocate a Public IP for gateway members. + Type: String + Default: false + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group. + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + DeployManagement: !Equals [!Ref ManagementDeploy, true] + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] +Resources: + GatewayLoadBalancer: + Type: AWS::ElasticLoadBalancingV2::LoadBalancer + Properties: + Type: gateway + Name: !Ref GWLBName + LoadBalancerAttributes: + - Key: load_balancing.cross_zone.enabled + Value: !Ref CrossZoneLoadBalancing + Subnets: !Ref GatewaysSubnets + Tags: + - Key: x-chkp-management + Value: !Ref ManagementServer + - Key: x-chkp-template + Value: !Ref ConfigurationTemplate + VpcEndpointService: + Type: AWS::EC2::VPCEndpointService + Properties: + AcceptanceRequired: !Ref AcceptConnectionRequired + GatewayLoadBalancerArns: + - !Ref GatewayLoadBalancer + TargetGroup: + Type: AWS::ElasticLoadBalancingV2::TargetGroup + Properties: + Name: !Ref TargetGroupName + Port: 6081 + Protocol: GENEVE + HealthCheckPort: 8117 + HealthCheckProtocol: TCP + TargetGroupAttributes: + - Key: deregistration_delay.timeout_seconds + Value: 20 + VpcId: !Ref VPC + TargetType: instance + Tags: + - Key: Name + Value: !Join + - "" + - - !Ref AWS::StackName + - "-tg1" + Listener: + Type: AWS::ElasticLoadBalancingV2::Listener + Properties: + DefaultActions: + - Type: forward + TargetGroupArn: !Ref TargetGroup + LoadBalancerArn: !Ref GatewayLoadBalancer + SecurityGatewaysStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/autoscale-gwlb.yaml + Parameters: + VPC: !Ref VPC + GatewaysSubnets: !Join [',', !Ref GatewaysSubnets] + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + Shell: !Ref Shell + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + MetaDataToken: !Ref MetaDataToken + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + AdminEmail: !Ref AdminEmail + GatewaysTargetGroups: !Ref TargetGroup + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + AllowUploadDownload: !Ref AllowUploadDownload + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + AllocatePublicAddress: !Ref AllocatePublicAddress + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + ManagementStack: + Type: AWS::CloudFormation::Stack + Condition: DeployManagement + Properties: + TemplateURL: __URL__/gwlb/management-gwlb.yaml + Parameters: + VPC: !Ref VPC + ManagementSubnet: !Select [0, !Ref GatewaysSubnets] + ManagementName: !Ref ManagementServer + ManagementInstanceType: !Ref ManagementInstanceType + KeyName: !Ref KeyName + Shell: !Ref Shell + VolumeEncryption: !If [VolumeEncryption, alias/aws/ebs, ''] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + ManagementPermissions: Create with read-write permissions + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + AllowUploadDownload: !Ref AllowUploadDownload + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + ManagementBootstrapScript: !Join + - ';' + - - 'echo -e "\nStarting Bootstrap script\n"' + - !Sub 'policy=${GatewaysPolicy} ; region=${AWS::Region} ; conf_template=${ConfigurationTemplate} ; mgmt=${ManagementServer}' + - !Sub ['version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - !Join ['', ['sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ' | base64 -d)"']] + - 'controller="gwlb-controller"' + - 'echo "Creating CME configuration"' + - 'autoprov_cfg -f init AWS -mn "${mgmt}" -tn "${conf_template}" -cn "${controller}" -po "${policy}" -otp "${sic}" -r "${region}" -ver "${version}" -iam' + - 'echo -e "\nFinished Bootstrap script\n"' +Outputs: + VPCID: + Description: VPC ID. + Value: !Ref VPC + ManagementPublicAddress: + Description: The public address of the management server. + Value: !GetAtt ManagementStack.Outputs.PublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !Ref ConfigurationTemplate + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name. + Value: gwlb-controller + GWLBName: + Description: Gateway Load Balancer Name. + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name. + Value: !Sub ['com.amazonaws.vpce.${AWS::Region}.${Service}', {Service: !Ref VpcEndpointService}] +Rules: + GatewayAddressAllocationRule: + RuleCondition: !Equals [!Ref ControlGatewayOverPrivateOrPublicAddress, 'public'] + Assertions: + - AssertDescription: "Gateway's selected to be provisioned by public IP, but ['AllocatePublicAddress'] parameter is false" + Assert: !Equals [!Ref AllocatePublicAddress, 'true'] diff --git a/deprecated/aws/templates/R80.40/gwlb/management-gwlb.yaml b/deprecated/aws/templates/R80.40/gwlb/management-gwlb.yaml new file mode 100755 index 00000000..d90c292e --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/management-gwlb.yaml @@ -0,0 +1,584 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Management Server (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - ManagementSubnet + - Label: + default: EC2 Instance Configuration + Parameters: + - ManagementName + - ManagementInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: IAM Permissions (ignored when the installation is not Primary Management + Server) + Parameters: + - ManagementPermissions + - ManagementPredefinedRole + - ManagementSTSRoles + - Label: + default: Check Point Settings + Parameters: + - ManagementVersion + - Shell + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - Label: + default: Security Management Server Settings + Parameters: + - ManagementHostname + - PrimaryManagement + - ManagementSICKey + - AllowUploadDownload + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + - ManagementBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + ManagementSubnet: + default: Management subnet + ManagementName: + default: Management name + ManagementInstanceType: + default: Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + ManagementPermissions: + default: IAM role + ManagementPredefinedRole: + default: Existing IAM role name + ManagementSTSRoles: + default: STS roles + ManagementVersion: + default: Version & license + Shell: + default: Admin shell + ManagementPasswordHash: + default: Password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + ManagementHostname: + default: Management hostname + PrimaryManagement: + default: Primary management + ManagementSICKey: + default: SIC key + AllowUploadDownload: + default: Allow upload & download + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Gateways management + GatewaysAddresses: + default: Gateways addresses + ManagementBootstrapScript: + default: Management bootstrap script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ManagementSubnet: + Description: To access the instance from the internet, make sure the subnet has + a route to the internet + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ManagementName: + Description: The Management name tag. + Type: String + Default: Check-Point-Management + ManagementInstanceType: + Description: The instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an elastic IP for the Management. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + ManagementPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored + if IAM role is not set to 'Use existing'. + Type: String + Default: '' + ManagementSTSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated + list of ARNs, without spaces). Ignored if IAM role is set to 'None' or 'Use + existing'. + Type: CommaDelimitedList + Default: '' + ManagementVersion: + Description: The license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementHostname: + Description: (optional) + Type: String + Default: mgmt-aws + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + PrimaryManagement: + Description: Determines if this is the primary Management Server or not. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementSICKey: + Description: >- + Mandatory only if deploying a secondary Management Server, the Secure Internal + Communication key creates trusted connections between Check Point components. + Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + Default: '' + AllowedPattern: '(|[a-zA-Z0-9]{8,})' + ConstraintDescription: Can be empty if this is a primary Management Server. Otherwise, + at least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate + with the Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Management. + Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage + are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + ManagementBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '[\.a-zA-Z0-9\-]*' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '[\.a-zA-Z0-9\-]*' +Conditions: + EIP: !Equals [!Ref AllocatePublicAddress, true] + ManageOverInternet: !Equals [!Ref GatewayManagement, Over the internet] + ManageOverInternetAndEIP: !And [!Condition EIP, !Condition ManageOverInternet] + CreateRole: !Or + - !Equals [!Ref ManagementPermissions, Create with assume role permissions (specify an STS role ARN)] + - !Equals [!Ref ManagementPermissions, Create with read permissions] + - !Equals [!Ref ManagementPermissions, Create with read-write permissions] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + UseRole: !Not [!Equals [!Ref ManagementPermissions, None (configure later)]] + NoSIC: !Equals [!Ref ManagementSICKey, ''] + PreRole: !And [!Condition UseRole, !Not [!Condition CreateRole]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref ManagementVersion, MGMT]] + ManagementReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: EIP + Properties: {} + ManagementReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: EIP + DependsOn: ManagementInstance + Properties: + Handle: !Ref ManagementReadyHandle + Timeout: 1800 + ManagementSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Management security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 257 + ToPort: 257 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 8211 + ToPort: 8211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18191 + ToPort: 18191 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18192 + ToPort: 18192 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18208 + ToPort: 18208 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18210 + ToPort: 18210 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18211 + ToPort: 18211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18221 + ToPort: 18221 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18264 + ToPort: 18264 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 22 + ToPort: 22 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 443 + ToPort: 443 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 18190 + ToPort: 18190 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 19009 + ToPort: 19009 + ManagementRoleStack: + Type: AWS::CloudFormation::Stack + Condition: CreateRole + Properties: + TemplateURL: __URL__/gwlb/cme-iam-role-gwlb.yaml + Parameters: + Permissions: !Ref ManagementPermissions + STSRoles: !Join [',', !Ref ManagementSTSRoles] + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: PreRole + Properties: + Path: / + Roles: + - !Ref ManagementPredefinedRole + ManagementInstance: + Type: AWS::EC2::Instance + DependsOn: ManagementLaunchTemplate + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref ManagementLaunchTemplate + Version: !GetAtt ManagementLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref ManagementName + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: false + Description: eth0 + GroupSet: + - !Ref ManagementSecurityGroup + DeleteOnTermination: true + SubnetId: !Ref ManagementSubnet + ManagementLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref ManagementInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [ UseRole, !If [ PreRole, !Ref InstanceProfile, !GetAtt ManagementRoleStack.Outputs.CMEIAMRole ], !Ref 'AWS::NoValue' ] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; hostname=${ManagementHostname} ; primary_mgmt=${PrimaryManagement} ; eic=${EnableInstanceConnect} ; admin_subnet=${AdminCIDR} ; eip=${AllocatePublicAddress} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary}' + - !If [EIP, !Sub ' wait_handle=''${ManagementReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [NoSIC, ' sic=""', !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref ManagementSICKey, ')"']]] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref ManagementPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref ManagementMaintenancePasswordHash, ')"']] + - !If [ManageOverInternetAndEIP, ' pub_mgmt=true', ' pub_mgmt=false'] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref ManagementBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref ManagementVersion]]}] + - ' python3 /etc/cloud_config.py waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" installationType=\"management\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"management_gwlb\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" primary=\"${primary_mgmt}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" adminSubnet=\"${admin_subnet}\" allocatePublicAddress=\"${eip}\" overTheInternet=\"${pub_mgmt}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + PublicAddress: + Type: AWS::EC2::EIP + Condition: EIP + Properties: + Domain: vpc + AddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: EIP + DependsOn: ManagementInstance + Properties: + InstanceId: !Ref ManagementInstance + AllocationId: !GetAtt PublicAddress.AllocationId +Outputs: + PublicAddress: + Condition: EIP + Description: The public address of the Management Server. + Value: !Ref PublicAddress + SSH: + Condition: EIP + Description: SSH command. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref PublicAddress]] + URL: + Condition: EIP + Description: URL to the portal. + Value: !Join ['', ['https://', !Ref PublicAddress]] diff --git a/deprecated/aws/templates/R80.40/gwlb/tgw-gwlb-master.yaml b/deprecated/aws/templates/R80.40/gwlb/tgw-gwlb-master.yaml new file mode 100755 index 00000000..051781e3 --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/tgw-gwlb-master.yaml @@ -0,0 +1,873 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, Gateway Load Balancer Endpoints and NAT Gateways for each AZ, in a new VPC for Transit Gateway (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - TgwSubnet1CIDR + - TgwSubnet2CIDR + - TgwSubnet3CIDR + - TgwSubnet4CIDR + - NatGwSubnet1CIDR + - NatGwSubnet2CIDR + - NatGwSubnet3CIDR + - NatGwSubnet4CIDR + - GWLBeSubnet1CIDR + - GWLBeSubnet2CIDR + - GWLBeSubnet3CIDR + - GWLBeSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - AllocatePublicAddress + - CloudWatch + - GatewayBootstrapScript + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PublicSubnet3CIDR: + default: Public subnet 3 CIDR + PublicSubnet4CIDR: + default: Public subnet 4 CIDR + TgwSubnet1CIDR: + default: TGW subnet 1 CIDR + TgwSubnet2CIDR: + default: TGW subnet 2 CIDR + TgwSubnet3CIDR: + default: TGW subnet 3 CIDR + TgwSubnet4CIDR: + default: TGW subnet 4 CIDR + NatGwSubnet1CIDR: + default: NAT subnet 1 CIDR + NatGwSubnet2CIDR: + default: NAT subnet 2 CIDR + NatGwSubnet3CIDR: + default: NAT subnet 3 CIDR + NatGwSubnet4CIDR: + default: NAT subnet 4 CIDR + GWLBeSubnet1CIDR: + default: Gateway Load Balancer Endpoint subnet 1 CIDR + GWLBeSubnet2CIDR: + default: Gateway Load Balancer Endpoint subnet 2 CIDR + GWLBeSubnet3CIDR: + default: Gateway Load Balancer Endpoint subnet 3 CIDR + GWLBeSubnet4CIDR: + default: Gateway Load Balancer Endpoint subnet 4 CIDR + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + AllocatePublicAddress: + default: Allocate Public IPs + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Gateways bootstrap script + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved). + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + VPCCIDR: + Description: The CIDR block of the provided VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet3CIDR: + Description: CIDR block for public subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet4CIDR: + Description: CIDR block for public subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet1CIDR: + Description: CIDR block for TGW subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.12.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet2CIDR: + Description: CIDR block for TGW subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.22.0/24 + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet3CIDR: + Description: CIDR block for TGW subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.32.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet4CIDR: + Description: CIDR block for TGW subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.42.0/24 + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + NatGwSubnet1CIDR: + Description: CIDR block for NAT subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.13.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + NatGwSubnet2CIDR: + Description: CIDR block for NAT subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.23.0/24 + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + NatGwSubnet3CIDR: + Description: CIDR block for NAT subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.33.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + NatGwSubnet4CIDR: + Description: CIDR block for NAT subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.43.0/24 + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet1CIDR: + Description: CIDR block for GWLBe subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.14.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet2CIDR: + Description: CIDR block for GWLBe subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.24.0/24 + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet3CIDR: + Description: CIDR block for GWLBe subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.34.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet4CIDR: + Description: CIDR block for GWLBe subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.44.0/24 + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: gwlb-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: gwlb-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + AllowedPattern: '^([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])$' + Default: gwlb1 + MaxLength: 32 + ConstraintDescription: Must be a valid GWLB Name + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + AllowedPattern: '^([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])$' + Default: tg1 + MaxLength: 32 + ConstraintDescription: Must be a valid target group name. + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + AllocatePublicAddress: + Description: Allocate a Public IP for gateway members. + Type: String + Default: false + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group. + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PublicSubnet3CIDR: !Ref PublicSubnet3CIDR + PublicSubnet4CIDR: !Ref PublicSubnet4CIDR + CreatePrivateSubnets: false + CreateAttachmentSubnets: true + AttachmentSubnet1CIDR: !Ref TgwSubnet1CIDR + AttachmentSubnet2CIDR: !Ref TgwSubnet2CIDR + AttachmentSubnet3CIDR: !Ref TgwSubnet3CIDR + AttachmentSubnet4CIDR: !Ref TgwSubnet4CIDR + TgwGwlbStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/tgw-gwlb.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + IGWID: !GetAtt VPCStack.Outputs.IGWID + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + GatewaysSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.PublicSubnet1ID + - !GetAtt VPCStack.Outputs.PublicSubnet2ID + - !If [3AZs, !GetAtt VPCStack.Outputs.PublicSubnet3ID, !Ref 'AWS::NoValue'] + - !If [4AZs, !GetAtt VPCStack.Outputs.PublicSubnet4ID, !Ref 'AWS::NoValue'] + TgwSubnet1Id: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + TgwSubnet2Id: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + TgwSubnet3Id: !If [3AZs, !GetAtt VPCStack.Outputs.AttachmentSubnet3ID, ""] + TgwSubnet4Id: !If [4AZs, !GetAtt VPCStack.Outputs.AttachmentSubnet4ID, ""] + NatGwSubnet1CIDR: !Ref NatGwSubnet1CIDR + NatGwSubnet2CIDR: !Ref NatGwSubnet2CIDR + NatGwSubnet3CIDR: !Ref NatGwSubnet3CIDR + NatGwSubnet4CIDR: !Ref NatGwSubnet4CIDR + GWLBeSubnet1CIDR: !Ref GWLBeSubnet1CIDR + GWLBeSubnet2CIDR: !Ref GWLBeSubnet2CIDR + GWLBeSubnet3CIDR: !Ref GWLBeSubnet3CIDR + GWLBeSubnet4CIDR: !Ref GWLBeSubnet4CIDR + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + AllowUploadDownload: !Ref AllowUploadDownload + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + AdminEmail: !Ref AdminEmail + Shell: !Ref Shell + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + AllocatePublicAddress: !Ref AllocatePublicAddress + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + GWLBName: !Ref GWLBName + TargetGroupName: !Ref TargetGroupName + CrossZoneLoadBalancing: !Ref CrossZoneLoadBalancing + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + GatewaysPolicy: !Ref GatewaysPolicy + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses +Outputs: + VPCID: + Description: VPC ID. + Value: !GetAtt VPCStack.Outputs.VPCID + ManagementPublicAddress: + Description: The public address of the management server. + Value: !GetAtt TgwGwlbStack.Outputs.ManagementPublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !GetAtt TgwGwlbStack.Outputs.ConfigurationTemplateName + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name. + Value: !GetAtt TgwGwlbStack.Outputs.ControllerName + GWLBName: + Description: Gateway Load Balancer Name. + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name. + Value: !GetAtt TgwGwlbStack.Outputs.GWLBServiceName + TgwSubnet1ID: + Description: TGW subnet 1 ID in Availability Zone 1. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + TgwSubnet2ID: + Description: TGW subnet 2 ID in Availability Zone 2. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + TgwSubnet3ID: + Description: TGW subnet 3 ID in Availability Zone 3. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet3ID + Condition: 3AZs + TgwSubnet4ID: + Description: TGW subnet 4 ID in Availability Zone 4. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet4ID + Condition: 4AZs + TgwSubnet1CIDR: + Description: TGW subnet 1 CIDR in Availability Zone 1. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet1CIDR + TgwSubnet2CIDR: + Description: TGW subnet 2 CIDR in Availability Zone 2. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet2CIDR + TgwSubnet3CIDR: + Description: TGW subnet 3 CIDR in Availability Zone 3. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet3CIDR + Condition: 3AZs + TgwSubnet4CIDR: + Description: TGW subnet 4 CIDR in Availability Zone 4. + Value: !GetAtt VPCStack.Outputs.AttachmentSubnet4CIDR + Condition: 4AZs +Rules: + GatewayAddressAllocationRule: + RuleCondition: !Equals [!Ref ControlGatewayOverPrivateOrPublicAddress, 'public'] + Assertions: + - AssertDescription: "Gateway's selected to be provisioned by public IP, but ['AllocatePublicAddress'] parameter is false" + Assert: !Equals [!Ref AllocatePublicAddress, 'true'] diff --git a/deprecated/aws/templates/R80.40/gwlb/tgw-gwlb.yaml b/deprecated/aws/templates/R80.40/gwlb/tgw-gwlb.yaml new file mode 100755 index 00000000..72823cfb --- /dev/null +++ b/deprecated/aws/templates/R80.40/gwlb/tgw-gwlb.yaml @@ -0,0 +1,1221 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Gateway Load Balancer, Check Point CloudGuard IaaS Security Gateway Auto Scaling Group, and optionally a Security Management Server, Gateway Load Balancer Endpoints and NAT Gateways for each AZ, in an existing VPC for Transit Gateway (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - IGWID + - AvailabilityZones + - NumberOfAZs + - GatewaysSubnets + - TgwSubnet1Id + - TgwSubnet2Id + - TgwSubnet3Id + - TgwSubnet4Id + - NatGwSubnet1CIDR + - NatGwSubnet2CIDR + - NatGwSubnet3CIDR + - NatGwSubnet4CIDR + - GWLBeSubnet1CIDR + - GWLBeSubnet2CIDR + - GWLBeSubnet3CIDR + - GWLBeSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - ManagementServer + - ConfigurationTemplate + - AdminEmail + - Shell + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - ControlGatewayOverPrivateOrPublicAddress + - AllocatePublicAddress + - CloudWatch + - GatewayBootstrapScript + - Label: + default: Gateway Load Balancer Configuration + Parameters: + - GWLBName + - TargetGroupName + - CrossZoneLoadBalancing + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - GatewaysPolicy + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + ParameterLabels: + VPC: + default: VPC + IGWID: + default: Internet Gateway ID + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + GatewaysSubnets: + default: Gateways subnets + TgwSubnet1Id: + default: Transit Gateway Attachment subnet 1 Id + TgwSubnet2Id: + default: Transit Gateway Attachment subnet 2 Id + TgwSubnet3Id: + default: Transit Gateway Attachment subnet 3 Id + TgwSubnet4Id: + default: Transit Gateway Attachment subnet 4 Id + NatGwSubnet1CIDR: + default: NAT subnet 1 CIDR + NatGwSubnet2CIDR: + default: NAT subnet 2 CIDR + NatGwSubnet3CIDR: + default: NAT subnet 3 CIDR + NatGwSubnet4CIDR: + default: NAT subnet 4 CIDR + GWLBeSubnet1CIDR: + default: Gateway Load Balancer Endpoint subnet 1 CIDR + GWLBeSubnet2CIDR: + default: Gateway Load Balancer Endpoint subnet 2 CIDR + GWLBeSubnet3CIDR: + default: Gateway Load Balancer Endpoint subnet 3 CIDR + GWLBeSubnet4CIDR: + default: Gateway Load Balancer Endpoint subnet 4 CIDR + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + AdminEmail: + default: Email address + Shell: + default: Admin shell + GatewayName: + default: Gateways instance name + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + AllocatePublicAddress: + default: Allocate Public IPs + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Gateways bootstrap script + GWLBName: + default: Gateway Load Balancer Name + TargetGroupName: + default: Target Group Name + CrossZoneLoadBalancing: + default: Enable Cross Zone Load Balancing + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Management instance type + ManagementVersion: + default: Management version & license + ManagementPasswordHash: + default: Management password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + GatewaysPolicy: + default: Security Policy + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: You must select a VPC. + IGWID: + Description: VPC's Internet Gateway Id (e.g. igw-123a4567). + Type: String + MinLength: 1 + ConstraintDescription: You must insert an Internet Gateway Id. + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved). + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + GatewaysSubnets: + Description: Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet. + Type: List + MinLength: 2 + TgwSubnet1Id: + Description: The TGW attachment subnet ID located in the 1st Availability Zone. + Type: String + MinLength: 1 + ConstraintDescription: You must insert Tgw Subnet Id for Availability Zone 1. + TgwSubnet2Id: + Description: The TGW attachment subnet ID located in the 2nd Availability Zone. + Type: String + MinLength: 1 + ConstraintDescription: You must insert Tgw Subnet Id for Availability Zone 2. + TgwSubnet3Id: + Description: The TGW attachment subnet ID located in the 3rd Availability Zone. + Type: String + TgwSubnet4Id: + Description: The TGW attachment subnet ID located in the 4th Availability Zone. + Type: String + NatGwSubnet1CIDR: + Description: CIDR block for NAT subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.13.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + NatGwSubnet2CIDR: + Description: CIDR block for NAT subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.23.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + NatGwSubnet3CIDR: + Description: CIDR block for NAT subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.33.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + NatGwSubnet4CIDR: + Description: CIDR block for NAT subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.43.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet1CIDR: + Description: CIDR block for GWLBe subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.14.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet2CIDR: + Description: CIDR block for GWLBe subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.24.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet3CIDR: + Description: CIDR block for GWLBe subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.34.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GWLBeSubnet4CIDR: + Description: CIDR block for GWLBe subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.44.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: gwlb-management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: gwlb-ASG-configuration + MinLength: 1 + MaxLength: 30 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + Shell: + Description: Change the admin shell to enable advanced command line configuration. Applies for Security Gateways and Security Management Server if deployed. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type. + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG-NGTP + - R80.40-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + AllocatePublicAddress: + Description: Allocate a Public IP for gateway members. + Type: String + Default: false + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + GWLBName: + Description: Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: gwlb1 + ConstraintDescription: Must be a valid GWLB Name + TargetGroupName: + Description: Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen. + Type: String + Default: tg1 + ConstraintDescription: Must be a valid target group name. + CrossZoneLoadBalancing: + Description: Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type. + ManagementVersion: + Description: The license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaysPolicy: + Description: The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group. + Type: String + Default: Standard + MinLength: 1 + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] +Resources: + GWLBeSubnet1: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 1 + - Key: Network + Value: Private + GWLBeSubnet2: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 2 + - Key: Network + Value: Private + GWLBeSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 3 + - Key: Network + Value: Private + GWLBeSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref GWLBeSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: GWLBe subnet 4 + - Key: Network + Value: Private + GWLBeSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 1 Route Table + - Key: Network + Value: Private + GWLBeSubnet1NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway1 + RouteTableId: !Ref GWLBeSubnet1RouteTable + GWLBeSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref GWLBeSubnet1RouteTable + SubnetId: !Ref GWLBeSubnet1 + GWLBeSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 2 Route Table + - Key: Network + Value: Private + GWLBeSubnet2NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway2 + RouteTableId: !Ref GWLBeSubnet2RouteTable + GWLBeSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref GWLBeSubnet2RouteTable + SubnetId: !Ref GWLBeSubnet2 + GWLBeSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 3 Route Table + - Key: Network + Value: Private + GWLBeSubnet3NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway3 + RouteTableId: !Ref GWLBeSubnet3RouteTable + GWLBeSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref GWLBeSubnet3RouteTable + SubnetId: !Ref GWLBeSubnet3 + GWLBeSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: GWLBe Subnet 4 Route Table + - Key: Network + Value: Private + GWLBeSubnet4NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NatGatewayId: !Ref NatGateway4 + RouteTableId: !Ref GWLBeSubnet4RouteTable + GWLBeSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref GWLBeSubnet4RouteTable + SubnetId: !Ref GWLBeSubnet4 + NatGwSubnet1: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 1 + - Key: Network + Value: Private + NatGwSubnet2: + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 2 + - Key: Network + Value: Private + NatGwSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 3 + - Key: Network + Value: Private + NatGwSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZs + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref NatGwSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: NAT subnet 4 + - Key: Network + Value: Private + NatGwSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 1 Route Table + - Key: Network + Value: Public + NatGwSubnet1NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet1RouteTable + NatGwSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref NatGwSubnet1RouteTable + SubnetId: !Ref NatGwSubnet1 + NatGwSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 2 Route Table + - Key: Network + Value: Public + NatGwSubnet2NatGwDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet2RouteTable + NatGwSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref NatGwSubnet2RouteTable + SubnetId: !Ref NatGwSubnet2 + NatGwSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 3 Route Table + - Key: Network + Value: Public + NatGwSubnet3NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet3RouteTable + NatGwSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref NatGwSubnet3RouteTable + SubnetId: !Ref NatGwSubnet3 + NatGwSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: NAT Subnet 4 Route Table + - Key: Network + Value: Public + NatGwSubnet4NatGwDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref IGWID + RouteTableId: !Ref NatGwSubnet4RouteTable + NatGwSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref NatGwSubnet4RouteTable + SubnetId: !Ref NatGwSubnet4 + GWLBStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gwlb/gwlb.yaml + Parameters: + VPC: !Ref VPC + GatewaysSubnets: !Join [',', !Ref GatewaysSubnets] + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + AllowUploadDownload: !Ref AllowUploadDownload + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate + AdminEmail: !Ref AdminEmail + Shell: !Ref Shell + GWLBName: !Ref GWLBName + TargetGroupName: !Ref TargetGroupName + AcceptConnectionRequired: false + CrossZoneLoadBalancing: !Ref CrossZoneLoadBalancing + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + AllocatePublicAddress: !Ref AllocatePublicAddress + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + GatewaysPolicy: !Ref GatewaysPolicy + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + GWLBe1: + DependsOn: [GWLBStack, GWLBeSubnet1] + Type: AWS::EC2::VPCEndpoint + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet1 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe2: + DependsOn: [GWLBStack, GWLBeSubnet2] + Type: AWS::EC2::VPCEndpoint + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet2 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe3: + DependsOn: [GWLBStack, GWLBeSubnet3] + Type: AWS::EC2::VPCEndpoint + Condition: 3AZs + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet3 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + GWLBe4: + DependsOn: [GWLBStack, GWLBeSubnet4] + Type: AWS::EC2::VPCEndpoint + Condition: 4AZs + Properties: + VpcId: !Ref VPC + VpcEndpointType: GatewayLoadBalancer + SubnetIds: + - !Ref GWLBeSubnet4 + ServiceName: !GetAtt GWLBStack.Outputs.GWLBServiceName + TGWAttachmentSubnet1RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: TGW Attachment Subnet 1 Route Table + - Key: Network + Value: Private + TGWAttachmentSubnet1GWLBeDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe1 + RouteTableId: !Ref TGWAttachmentSubnet1RouteTable + TGWAttachmentSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref TGWAttachmentSubnet1RouteTable + SubnetId: !Ref TgwSubnet1Id + TGWAttachmentSubnet2RouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: TGW Attachment Subnet 2 Route Table + - Key: Network + Value: Private + TGWAttachmentSubnet2GWLBeDefaultRoute: + Type: AWS::EC2::Route + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe2 + RouteTableId: !Ref TGWAttachmentSubnet2RouteTable + TGWAttachmentSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref TGWAttachmentSubnet2RouteTable + SubnetId: !Ref TgwSubnet2Id + TGWAttachmentSubnet3RouteTable: + Type: AWS::EC2::RouteTable + Condition: 3AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: TGW Attachment Subnet 3 Route Table + - Key: Network + Value: Private + TGWAttachmentSubnet3GWLBeDefaultRoute: + Type: AWS::EC2::Route + Condition: 3AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe3 + RouteTableId: !Ref TGWAttachmentSubnet3RouteTable + TGWAttachmentSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + Properties: + RouteTableId: !Ref TGWAttachmentSubnet3RouteTable + SubnetId: !Ref TgwSubnet3Id + TGWAttachmentSubnet4RouteTable: + Type: AWS::EC2::RouteTable + Condition: 4AZs + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: TGW Attachment Subnet 4 Route Table + - Key: Network + Value: Private + TGWAttachmentSubnet4GWLBeDefaultRoute: + Type: AWS::EC2::Route + Condition: 4AZs + Properties: + DestinationCidrBlock: 0.0.0.0/0 + VpcEndpointId: !Ref GWLBe4 + RouteTableId: !Ref TGWAttachmentSubnet4RouteTable + TGWAttachmentSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + Properties: + RouteTableId: !Ref TGWAttachmentSubnet4RouteTable + SubnetId: !Ref TgwSubnet4Id + NatGwPublicAddress1: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + NatGwPublicAddress2: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + NatGwPublicAddress3: + Type: AWS::EC2::EIP + Condition: 3AZs + Properties: + Domain: vpc + NatGwPublicAddress4: + Type: AWS::EC2::EIP + Condition: 4AZs + Properties: + Domain: vpc + NatGateway1: + DependsOn: [GWLBStack, NatGwSubnet1] + Type: AWS::EC2::NatGateway + Properties: + AllocationId: !GetAtt NatGwPublicAddress1.AllocationId + SubnetId: !Ref NatGwSubnet1 + Tags: + - Key: Name + Value: NatGW1 + NatGateway2: + DependsOn: [GWLBStack, NatGwSubnet2] + Type: AWS::EC2::NatGateway + Properties: + AllocationId: !GetAtt NatGwPublicAddress2.AllocationId + SubnetId: !Ref NatGwSubnet2 + Tags: + - Key: Name + Value: NatGW2 + NatGateway3: + DependsOn: [GWLBStack, NatGwSubnet3] + Type: AWS::EC2::NatGateway + Condition: 3AZs + Properties: + AllocationId: !GetAtt NatGwPublicAddress3.AllocationId + SubnetId: !Ref NatGwSubnet3 + Tags: + - Key: Name + Value: NatGW3 + NatGateway4: + DependsOn: [GWLBStack, NatGwSubnet4] + Type: AWS::EC2::NatGateway + Condition: 4AZs + Properties: + AllocationId: !GetAtt NatGwPublicAddress4.AllocationId + SubnetId: !Ref NatGwSubnet4 + Tags: + - Key: Name + Value: NatGW4 +Outputs: + ManagementPublicAddress: + Description: The public address of the management server. + Value: !GetAtt GWLBStack.Outputs.ManagementPublicAddress + Condition: DeployManagement + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !GetAtt GWLBStack.Outputs.ConfigurationTemplateName + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name. + Value: !GetAtt GWLBStack.Outputs.ControllerName + GWLBName: + Description: Gateway Load Balancer Name. + Value: !Ref GWLBName + GWLBServiceName: + Description: Gateway Load Balancer Service Name. + Value: !GetAtt GWLBStack.Outputs.GWLBServiceName +Rules: + GatewayAddressAllocationRule: + RuleCondition: !Equals [!Ref ControlGatewayOverPrivateOrPublicAddress, 'public'] + Assertions: + - AssertDescription: "Gateway's selected to be provisioned by public IP, but ['AllocatePublicAddress'] parameter is false" + Assert: !Equals [!Ref AllocatePublicAddress, 'true'] diff --git a/deprecated/aws/templates/R80.40/iam/cloudwatch-policy.yaml b/deprecated/aws/templates/R80.40/iam/cloudwatch-policy.yaml new file mode 100755 index 00000000..a9a233e8 --- /dev/null +++ b/deprecated/aws/templates/R80.40/iam/cloudwatch-policy.yaml @@ -0,0 +1,39 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for selected permissions (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Policy Attributes + Parameters: + - PolicyName + - PolicyRole + ParameterLabels: + PolicyName: + default: Policy name + PolicyRole: + default: IAM role name +Parameters: + PolicyName: + Description: '' + Type: String + Default: 'Cloudwatch' + AllowedPattern: '[\w+=,.@-]+' + PolicyRole: + Description: '' + Type: String + AllowedPattern: '[\w+=,.@-]+' +Resources: + IAMPolicy: + Type: AWS::IAM::Policy + Properties: + PolicyName: !Sub "${PolicyName}-iam-policy" + PolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Action: + - cloudwatch:PutMetricData + Resource: '*' + Roles: + - !Ref PolicyRole diff --git a/deprecated/aws/templates/R80.40/iam/cluster-iam-role.yaml b/deprecated/aws/templates/R80.40/iam/cluster-iam-role.yaml new file mode 100755 index 00000000..85d52102 --- /dev/null +++ b/deprecated/aws/templates/R80.40/iam/cluster-iam-role.yaml @@ -0,0 +1,35 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for selected permissions (__VERSION__) +Resources: + ClusterIAMRole: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: [ec2.amazonaws.com] + Action: sts:AssumeRole + Path: / + Policies: + - PolicyName: ClusterPolicy + PolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Action: + - ec2:AssignPrivateIpAddresses + - ec2:AssociateAddress + - ec2:CreateRoute + - ec2:DescribeNetworkInterfaces + - ec2:DescribeRouteTables + - ec2:ReplaceRoute + Resource: '*' +Outputs: + ClusterIAMRole: + Description: The IAM role. + Value: !Ref ClusterIAMRole + ClusterARNRole: + Description: The IAM role ARN. + Value: !GetAtt ClusterIAMRole.Arn diff --git a/deprecated/aws/templates/R80.40/iam/cme-iam-role.yaml b/deprecated/aws/templates/R80.40/iam/cme-iam-role.yaml new file mode 100755 index 00000000..b9f6c2bf --- /dev/null +++ b/deprecated/aws/templates/R80.40/iam/cme-iam-role.yaml @@ -0,0 +1,159 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for selected permissions (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: IAM + Parameters: + - Permissions + - Label: + default: Advanced Configuration (optional) + Parameters: + - STSRoles + - TrustedAccount + ParameterLabels: + Permissions: + default: IAM role + STSRoles: + default: STS roles + TrustedAccount: + default: Trusted Account ID +Parameters: + Permissions: + Type: String + Default: Create with read permissions + AllowedValues: + - Create with read permissions + - Create with read-write permissions + - Create with assume role permissions (specify an STS role ARN) + STSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated list of ARNs, without spaces). + Type: String + Default: '' + TrustedAccount: + Description: A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it. + Type: String + Default: '' + AllowedPattern: '^([0-9]{12})|$' +Conditions: + AllowReadPermissions: !Or + - !Equals [!Ref Permissions, Create with read permissions] + - !Equals [!Ref Permissions, Create with read-write permissions] + AllowWritePermissions: !Equals [!Ref Permissions, Create with read-write permissions] + ProvidedSTSRoles: !Not [!Equals [!Ref STSRoles, '']] + NotProvidedTrustedAccount: !Equals ['', !Ref TrustedAccount] + ProvidedTrustedAccount: !Not [!Condition NotProvidedTrustedAccount] +Resources: + CMEIAMRole: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - ProvidedTrustedAccount + - Effect: Allow + Principal: + AWS: [!Ref TrustedAccount] + Action: ['sts:AssumeRole'] + - !Ref 'AWS::NoValue' + - !If + - NotProvidedTrustedAccount + - Effect: Allow + Principal: + Service: [ec2.amazonaws.com] + Action: ['sts:AssumeRole'] + - !Ref 'AWS::NoValue' + Path: / + Policies: + - PolicyName: CMEPolicy + PolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - ProvidedSTSRoles + - Effect: Allow + Action: ['sts:AssumeRole'] + Resource: !Split [',', !Ref STSRoles] + - !Ref 'AWS::NoValue' + - !If + - AllowReadPermissions + - Effect: Allow + Action: + - autoscaling:DescribeAutoScalingGroups + - ec2:DescribeRegions + - ec2:DescribeCustomerGateways + - ec2:DescribeInstances + - ec2:DescribeNetworkInterfaces + - ec2:DescribeRouteTables + - ec2:DescribeSecurityGroups + - ec2:DescribeSubnets + - ec2:DescribeTransitGateways + - ec2:DescribeTransitGatewayAttachments + - ec2:DescribeTransitGatewayRouteTables + - ec2:DescribeVpcs + - ec2:DescribeVpnGateways + - ec2:DescribeVpnConnections + - ec2:GetTransitGatewayAttachmentPropagations + - elasticloadbalancing:DescribeLoadBalancers + - elasticloadbalancing:DescribeTags + - elasticloadbalancing:DescribeListeners + - elasticloadbalancing:DescribeTargetGroups + - elasticloadbalancing:DescribeRules + - elasticloadbalancing:DescribeTargetHealth + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowWritePermissions + - Effect: Allow + Action: + - ec2:AssociateTransitGatewayRouteTable + - ec2:AttachVpnGateway + - ec2:CreateCustomerGateway + - ec2:CreateVpnConnection + - ec2:CreateVpnGateway + - ec2:DeleteCustomerGateway + - ec2:DeleteVpnConnection + - ec2:DeleteVpnGateway + - ec2:DetachVpnGateway + - ec2:DisableTransitGatewayRouteTablePropagation + - ec2:DisableVgwRoutePropagation + - ec2:DisassociateTransitGatewayRouteTable + - ec2:EnableTransitGatewayRouteTablePropagation + - ec2:EnableVgwRoutePropagation + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowWritePermissions + - Effect: Allow + Action: + - cloudformation:DescribeStacks + - cloudformation:DescribeStackResources + - cloudformation:ListStacks + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowWritePermissions + - Effect: Allow + Action: + - cloudformation:CreateStack + - cloudformation:DeleteStack + Resource: 'arn:aws:cloudformation:*:*:stack/vpn-by-tag--*/*' + - !Ref 'AWS::NoValue' + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + InstanceProfileName: !Ref CMEIAMRole + Roles: + - !Ref CMEIAMRole +Outputs: + CMEIAMRole: + Description: The IAM role. + Value: !Ref CMEIAMRole + CMEARNRole: + Description: The IAM role ARN. + Value: !GetAtt CMEIAMRole.Arn + InstanceProfile: + Description: The Instance Profile ARN. + Value: !GetAtt InstanceProfile.Arn \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/iam/sts-role.yaml b/deprecated/aws/templates/R80.40/iam/sts-role.yaml new file mode 100755 index 00000000..93f5cb40 --- /dev/null +++ b/deprecated/aws/templates/R80.40/iam/sts-role.yaml @@ -0,0 +1,119 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for cross account permissions (20190313) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Cross Account Permissions Configuration + Parameters: + - TrustedAccount + - Permissions + ParameterLabels: + TrustedAccount: + default: Trusted Account ID + STSPermissions: + default: IAM Role Permissions +Parameters: + TrustedAccount: + Description: A 12 digits number that represents the ID of the trusted account. + Type: String + AllowedPattern: '^[0-9]{12}$' + STSPermissions: + Description: Select Read-Write if you intend to use this role with Transit VPC. + Type: String + Default: Read only + AllowedValues: + - Read only + - Read-Write +Conditions: + AllowReadPermissions: !Or + - !Equals [!Ref STSPermissions, Read only] + - !Equals [!Ref STSPermissions, Read-Write] + AllowCreateVPNPermissions: !Equals [!Ref STSPermissions, Read-Write] +Resources: + Role: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + AWS: + - !Ref TrustedAccount + Action: + - sts:AssumeRole + Path: / + Policies: + - PolicyName: Policy + PolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - AllowReadPermissions + - Effect: Allow + Action: + - ec2:DescribeInstances + - ec2:DescribeNetworkInterfaces + - ec2:DescribeSubnets + - ec2:DescribeVpcs + - ec2:DescribeVpnGateways + - ec2:DescribeVpnConnections + - ec2:DescribeSecurityGroups + - elasticloadbalancing:DescribeLoadBalancers + - elasticloadbalancing:DescribeTags + - elasticloadbalancing:DescribeListeners + - elasticloadbalancing:DescribeTargetGroups + - elasticloadbalancing:DescribeRules + - elasticloadbalancing:DescribeTargetHealth + - autoscaling:DescribeAutoScalingGroups + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowCreateVPNPermissions + - Effect: Allow + Action: + - ec2:DescribeCustomerGateways + - ec2:CreateCustomerGateway + - ec2:DeleteCustomerGateway + - ec2:DescribeRouteTables + - ec2:EnableVgwRoutePropagation + - ec2:DisableVgwRoutePropagation + - ec2:DescribeVpnGateways + - ec2:CreateVpnGateway + - ec2:AttachVpnGateway + - ec2:DetachVpnGateway + - ec2:DeleteVpnGateway + - ec2:DescribeVpnConnections + - ec2:CreateVpnConnection + - ec2:DeleteVpnConnection + - ec2:DescribeTransitGateways + - ec2:DescribeTransitGatewayRouteTables + - ec2:DescribeTransitGatewayAttachments + - ec2:AssociateTransitGatewayRouteTable + - ec2:DisassociateTransitGatewayRouteTable + - ec2:EnableTransitGatewayRouteTablePropagation + - ec2:DisableTransitGatewayRouteTablePropagation + - ec2:GetTransitGatewayAttachmentPropagations + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowCreateVPNPermissions + - Effect: Allow + Action: + - cloudformation:DescribeStacks + - cloudformation:DescribeStackResources + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowCreateVPNPermissions + - Effect: Allow + Action: + - cloudformation:CreateStack + - cloudformation:DeleteStack + Resource: arn:aws:cloudformation:*:*:stack/vpn-by-tag--*/* + - !Ref 'AWS::NoValue' +Outputs: + Role: + Description: The role ARN to assume by the trusted account. + Value: !GetAtt Role.Arn diff --git a/deprecated/aws/templates/R80.40/management/management.yaml b/deprecated/aws/templates/R80.40/management/management.yaml new file mode 100755 index 00000000..c3ccc1d7 --- /dev/null +++ b/deprecated/aws/templates/R80.40/management/management.yaml @@ -0,0 +1,585 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Management Server (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - ManagementSubnet + - Label: + default: EC2 Instance Configuration + Parameters: + - ManagementName + - ManagementInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: IAM Permissions (ignored when the installation is not Primary Management + Server) + Parameters: + - ManagementPermissions + - ManagementPredefinedRole + - ManagementSTSRoles + - Label: + default: Check Point Settings + Parameters: + - ManagementVersion + - Shell + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - Label: + default: Security Management Server Settings + Parameters: + - ManagementHostname + - ManagementInstallationType + - SICKey + - AllowUploadDownload + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + - ManagementBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + ManagementSubnet: + default: Management subnet + ManagementName: + default: Management name + ManagementInstanceType: + default: Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + ManagementPermissions: + default: IAM role + ManagementPredefinedRole: + default: Existing IAM role name + ManagementSTSRoles: + default: STS roles + ManagementVersion: + default: Version & license + Shell: + default: Admin shell + ManagementPasswordHash: + default: Password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + ManagementHostname: + default: Management hostname + ManagementInstallationType: + default: Management installation type + SICKey: + default: SIC key + AllowUploadDownload: + default: Allow upload & download + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Gateways management + GatewaysAddresses: + default: Gateways addresses + ManagementBootstrapScript: + default: Management bootstrap script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ManagementSubnet: + Description: To access the instance from the internet, make sure the subnet has + a route to the internet. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ManagementName: + Description: The Management name tag. + Type: String + Default: Check-Point-Management + ManagementInstanceType: + Description: The instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an elastic IP for the Management. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + ManagementPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored. + if IAM role is not set to 'Use existing' + Type: String + Default: '' + ManagementSTSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated + list of ARNs, without spaces). Ignored if IAM role is set to 'None' or 'Use + existing'. + Type: CommaDelimitedList + Default: '' + ManagementVersion: + Description: The license to install on the Security Management Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + - R80.40-PAYG + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: mgmt-aws + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + ManagementInstallationType: + Description: Determines the Management Server installation type. + Type: String + Default: Primary management + AllowedValues: + - Primary management + - Secondary management + - Log Server + SICKey: + Description: >- + Mandatory only if deploying a secondary Management Server or Log Server, the Secure Internal + Communication key creates trusted connections between Check Point components. + Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + Default: '' + AllowedPattern: '(|[a-zA-Z0-9]{8,})' + ConstraintDescription: Can be empty if this is a primary Management Server. Otherwise, + at least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate + with the Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Management + Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage + are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + ManagementBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '[\.a-zA-Z0-9\-]*' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '[\.a-zA-Z0-9\-]*' +Conditions: + EIP: !Equals [!Ref AllocatePublicAddress, true] + ManageOverInternet: !Equals [!Ref GatewayManagement, Over the internet] + ManageOverInternetAndEIP: !And [!Condition EIP, !Condition ManageOverInternet] + CreateRole: !Or + - !Equals [!Ref ManagementPermissions, Create with assume role permissions (specify an STS role ARN)] + - !Equals [!Ref ManagementPermissions, Create with read permissions] + - !Equals [!Ref ManagementPermissions, Create with read-write permissions] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + UseRole: !Not [!Equals [!Ref ManagementPermissions, None (configure later)]] + NoSIC: !Equals [!Ref SICKey, ''] + PreRole: !And [!Condition UseRole, !Not [!Condition CreateRole]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref ManagementVersion, MGMT]] + ManagementReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: EIP + Properties: {} + ManagementReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: EIP + DependsOn: ManagementInstance + Properties: + Handle: !Ref ManagementReadyHandle + Timeout: 1800 + ManagementSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Management security group + VpcId: !Ref VPC + SecurityGroupIngress: + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 257 + ToPort: 257 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 8211 + ToPort: 8211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18191 + ToPort: 18191 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18192 + ToPort: 18192 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18208 + ToPort: 18208 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18210 + ToPort: 18210 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18211 + ToPort: 18211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18221 + ToPort: 18221 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18264 + ToPort: 18264 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 22 + ToPort: 22 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 443 + ToPort: 443 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 18190 + ToPort: 18190 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 19009 + ToPort: 19009 + ManagementRoleStack: + Type: AWS::CloudFormation::Stack + Condition: CreateRole + Properties: + TemplateURL: __URL__/iam/cme-iam-role.yaml + Parameters: + Permissions: !Ref ManagementPermissions + STSRoles: !Join [',', !Ref ManagementSTSRoles] + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: PreRole + Properties: + Path: / + Roles: + - !Ref ManagementPredefinedRole + ManagementInstance: + Type: AWS::EC2::Instance + DependsOn: ManagementLaunchTemplate + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref ManagementLaunchTemplate + Version: !GetAtt ManagementLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref ManagementName + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: false + Description: eth0 + GroupSet: + - !Ref ManagementSecurityGroup + DeleteOnTermination: true + SubnetId: !Ref ManagementSubnet + ManagementLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref ManagementInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [ UseRole, !If [ PreRole, !Ref InstanceProfile, !GetAtt ManagementRoleStack.Outputs.CMEIAMRole ], !Ref 'AWS::NoValue' ] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; hostname=${ManagementHostname} ; eic=${EnableInstanceConnect} ; admin_subnet=${AdminCIDR} ; eip=${AllocatePublicAddress} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; mgmt_install_type=''${ManagementInstallationType}''' + - !If [EIP, !Sub ' wait_handle=''${ManagementReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [NoSIC, ' sic=""', !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref SICKey, ')"']]] + - !If [ManageOverInternetAndEIP, ' pub_mgmt=true', ' pub_mgmt=false'] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref ManagementBootstrapScript, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref ManagementPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref ManagementMaintenancePasswordHash, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref ManagementVersion]]}] + - ' python3 /etc/cloud_config.py waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" installationType=\"management\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"management\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" "management_installation_type=\"${mgmt_install_type}\"" adminSubnet=\"${admin_subnet}\" allocatePublicAddress=\"${eip}\" overTheInternet=\"${pub_mgmt}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + PublicAddress: + Type: AWS::EC2::EIP + Condition: EIP + Properties: + Domain: vpc + AddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: EIP + DependsOn: ManagementInstance + Properties: + InstanceId: !Ref ManagementInstance + AllocationId: !GetAtt PublicAddress.AllocationId +Outputs: + PublicAddress: + Condition: EIP + Description: The public address of the Management Server. + Value: !Ref PublicAddress + SSH: + Condition: EIP + Description: SSH command. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref PublicAddress]] + URL: + Condition: EIP + Description: URL to the portal. + Value: !Join ['', ['https://', !Ref PublicAddress]] diff --git a/deprecated/aws/templates/R80.40/management/mds.yaml b/deprecated/aws/templates/R80.40/management/mds.yaml new file mode 100755 index 00000000..6099ed35 --- /dev/null +++ b/deprecated/aws/templates/R80.40/management/mds.yaml @@ -0,0 +1,529 @@ +AWSTemplateFormatVersion: '2010-09-09' +Description: Deploys a Check Point Multi-Domain Server (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - MDSSubnet + - Label: + default: EC2 Instance Configuration + Parameters: + - MDSName + - MDSInstanceType + - KeyName + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: IAM Permissions (ignored when the installation type is not Primary + Multi-Domain Server) + Parameters: + - MDSPermissions + - MDSPredefinedRole + - MDSSTSRoles + - Label: + default: Check Point Settings + Parameters: + - MDSVersion + - Shell + - MDSPasswordHash + - MDSMaintenancePasswordHash + - Label: + default: Multi-Domain Server Settings + Parameters: + - MDSHostname + - MDSInstallationType + - MDSSICKey + - AllowUploadDownload + - AdminCIDR + - GatewaysAddresses + - MDSBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + MDSSubnet: + default: MDS subnet + MDSName: + default: MDS name + MDSInstanceType: + default: Instance type + KeyName: + default: Key name + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + MDSPermissions: + default: IAM role + MDSPredefinedRole: + default: Existing IAM role name + MDSSTSRoles: + default: STS roles + MDSVersion: + default: Version & license + Shell: + default: Admin shell + MDSPasswordHash: + default: Password hash + MDSMaintenancePasswordHash: + default: MDS Maintenance Password hash + MDSHostname: + default: MDS hostname + MDSInstallationType: + default: MDS installation type + MDSSICKey: + default: SIC key + AllowUploadDownload: + default: Allow upload & download + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses + MDSBootstrapScript: + default: MDS Bootstrap script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + MDSSubnet: + Description: To access the instance from the internet, make sure the subnet has. + a route to the internet + Type: AWS::EC2::Subnet::Id + MinLength: 1 + MDSName: + Description: The MDS name tag. + Type: String + Default: Check-Point-MDS + MDSInstanceType: + Description: The instance type of the Multi-Domain Server. + Type: String + Default: m5.2xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + MDSPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + MDSPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored + if IAM role is not set to 'Use existing'. + Type: String + Default: '' + MDSSTSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated + list of ARNs, without spaces). Ignored if IAM role is set to 'None' or 'Use + existing'. + Type: CommaDelimitedList + Default: '' + MDSVersion: + Description: The license to install on the Multi-Domain Server. + Type: String + Default: R80.40-BYOL + AllowedValues: + - R80.40-BYOL + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + MDSPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + MDSMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + MDSHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: mds-aws + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + MDSInstallationType: + Description: Determines the Multi-Domain Server installation type. + Type: String + Default: Primary Multi-Domain Server + AllowedValues: + - Primary Multi-Domain Server + - Secondary Multi-Domain Server + - Multi-Domain Log Server + MDSSICKey: + Description: >- + Mandatory if deploying a Secondary Multi-Domain Server or Multi-Domain Log Server, + the Secure Internal Communication key creates trusted connections between Check + Point components. Choose a random string consisting of at least 8 alphanumeric + characters. + Type: String + Default: '' + AllowedPattern: '(|[a-zA-Z0-9]{8,})' + ConstraintDescription: Can be empty if this is a Primary Multi-Domain Server. + Otherwise, at least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate + with the Multi-Domain Server. The address should be either 0.0.0.0/0 (any address) or /32 (specific address) + Type: String + AllowedPattern: '^((0.0.0.0\/0)|)$|^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/32)$' + ConstraintDescription: Administrator address must be either 0.0.0.0/0 or /32 + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Multi-Domain. + Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + MDSBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '[\.a-zA-Z0-9\-]*' + NTPSecondary: + Description: (optional) + Type: String + Default: '0.pool.ntp.org' + AllowedPattern: '[\.a-zA-Z0-9\-]*' +Conditions: + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + CreateRole: !And + - !Or + - !Condition PrimaryMDS + - !Condition SecondaryMDS + - !Or + - !Equals [!Ref MDSPermissions, Create with assume role permissions (specify an STS role ARN)] + - !Equals [!Ref MDSPermissions, Create with read permissions] + - !Equals [!Ref MDSPermissions, Create with read-write permissions] + UseRole: !And [!Or [!Condition PrimaryMDS, !Condition SecondaryMDS], !Not [!Equals [!Ref MDSPermissions, None (configure later)]]] + PrimaryMDS: !Equals [!Ref MDSInstallationType, Primary Multi-Domain Server] + SecondaryMDS: !Equals [!Ref MDSInstallationType, Secondary Multi-Domain Server] + PreRole: !And [!Condition UseRole, !Not [!Condition CreateRole]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref MDSVersion, MGMT]] + MDSSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: MDS security group + VpcId: !Ref VPC + SecurityGroupIngress: + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 257 + ToPort: 257 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 8211 + ToPort: 8211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18191 + ToPort: 18191 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18192 + ToPort: 18192 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18208 + ToPort: 18208 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18210 + ToPort: 18210 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18211 + ToPort: 18211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18221 + ToPort: 18221 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18264 + ToPort: 18264 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 22 + ToPort: 22 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 443 + ToPort: 443 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 18190 + ToPort: 18190 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 19009 + ToPort: 19009 + MDSRoleStack: + Type: AWS::CloudFormation::Stack + Condition: CreateRole + Properties: + TemplateURL: __URL__/iam/cme-iam-role.yaml + Parameters: + Permissions: !Ref MDSPermissions + STSRoles: !Join [',', !Ref MDSSTSRoles] + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: PreRole + Properties: + Path: / + Roles: + - !Ref MDSPredefinedRole + MDSInstance: + Type: AWS::EC2::Instance + DependsOn: [MDSSecurityGroup, MDSLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MDSLaunchTemplate + Version: !GetAtt MDSLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref MDSName + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: false + Description: eth0 + GroupSet: + - !Ref MDSSecurityGroup + DeleteOnTermination: true + SubnetId: !Ref MDSSubnet + MDSLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref MDSInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [ UseRole, !If [ PreRole, !Ref InstanceProfile, !GetAtt MDSRoleStack.Outputs.CMEIAMRole ], !Ref 'AWS::NoValue' ] + UserData: !Base64 + Fn::Join: + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; hostname=${MDSHostname} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; admin_subnet=${AdminCIDR}' + - !If [PrimaryMDS, ' primary=true ; secondary=false', !If [SecondaryMDS, ' primary=false ; secondary=true', ' primary=false ; secondary=false']] + - !If [PrimaryMDS, ' sic=notused', !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref MDSSICKey, ')"']]] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref MDSBootstrapScript, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref MDSPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref MDSMaintenancePasswordHash, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref MDSVersion]]}] + - ' python3 /etc/cloud_config.py sicKey=\"${sic}\" installationType=\"mds\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"mds\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" primary=\"${primary}\" secondary=\"${secondary}\" adminSubnet=\"${admin_subnet}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/utils/copy-lambda-zip.yaml b/deprecated/aws/templates/R80.40/utils/copy-lambda-zip.yaml new file mode 100755 index 00000000..f5cdcfd2 --- /dev/null +++ b/deprecated/aws/templates/R80.40/utils/copy-lambda-zip.yaml @@ -0,0 +1,138 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Create an S3 bucket in the same region as the stack, and copy a zip of a Lambda from remote bucket to it (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Lambda zip location + Parameters: + - SourceBucketName + - FolderName + - LambdaPathObjects + ParameterLabels: + SourceBucketName: + default: Source Bucket Name + FolderName: + default: Folder Name + LambdaPathObjects: + default: Lambda Path +Parameters: + SourceBucketName: + Description: The source bucket (e.g. lambda-bucket ). + Type: String + MinLength: 1 + FolderName: + Description: The source folder (e.g. lambda-prefix/ ). + Type: String + AllowedPattern: '^[0-9a-zA-Z-_/]*/$' + LambdaPathObjects: + Description: A zip file (e.g. lambda.zip). + Type: String + AllowedPattern: '.*\.zip' +Resources: + LambdaZipBucket: + Type: AWS::S3::Bucket + CopyZips: + Type: Custom::CopyZips + Properties: + ServiceToken: !GetAtt CopyZipsFunction.Arn + SourceBucket: !Ref SourceBucketName + DestBucket: !Ref LambdaZipBucket + Prefix: !Ref FolderName + Objects: + - !Ref LambdaPathObjects + CopyZipsRole: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: lambda.amazonaws.com + Action: sts:AssumeRole + Path: / + Policies: + - PolicyName: !Sub lambda-copier-${LambdaZipBucket} + PolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Action: + - s3:GetObject + Resource: + - !Sub arn:aws:s3:::${SourceBucketName}/${FolderName}* + - Effect: Allow + Action: + - s3:PutObject + - s3:DeleteObject + Resource: + - !Sub arn:aws:s3:::${LambdaZipBucket}/${FolderName}* + CopyZipsFunction: + Type: AWS::Lambda::Function + Properties: + Description: Copies objects from a source S3 bucket to a destination. + Handler: index.handler + Runtime: python3.7 + Role: !GetAtt CopyZipsRole.Arn + Timeout: 240 + Code: + ZipFile: | + import json + import logging + import threading + import boto3 + import cfnresponse + + + def copy_objects(source_bucket, dest_bucket, prefix, objects): + s3 = boto3.client('s3') + for o in objects: + key = prefix + o + copy_source = {'Bucket': source_bucket, 'Key': key } + print(f'copy_source: {copy_source}') + print(f'dest_bucket = {dest_bucket}') + print(f'key = {key}') + s3.copy_object(CopySource=copy_source, Bucket=dest_bucket, Key=key) + + + def delete_objects(bucket, prefix, objects): + s3 = boto3.client('s3') + objects = {'Objects': [{'Key': prefix + o} for o in objects]} + s3.delete_objects(Bucket=bucket, Delete=objects) + + + def timeout(event, context): + logging.error('Execution is about to time out, sending failure' + ' response to CloudFormation') + cfnresponse.send(event, context, cfnresponse.FAILED, {}, None) + + + def handler(event, context): + # make sure we send a failure to CloudFormation if the function + # is going to timeout + timer = threading.Timer((context.get_remaining_time_in_millis() + / 1000.00) - 0.5, timeout, args=[event, context]) + timer.start() + + print(f'Received event: {json.dumps(event)}') + status = cfnresponse.SUCCESS + try: + source_bucket = event['ResourceProperties']['SourceBucket'] + dest_bucket = event['ResourceProperties']['DestBucket'] + prefix = event['ResourceProperties']['Prefix'] + objects = event['ResourceProperties']['Objects'] + if event['RequestType'] == 'Delete': + delete_objects(dest_bucket, prefix, objects) + else: + copy_objects(source_bucket, dest_bucket, prefix, objects) + except Exception as e: + logging.error('Exception: %s' % e, exc_info=True) + status = cfnresponse.FAILED + finally: + timer.cancel() + cfnresponse.send(event, context, status, {}, None) +Outputs: + LambdaZipBucket: + Description: The new S3 bucket in the local region. + Value: !Ref LambdaZipBucket \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/utils/tap-target-and-filter.yaml b/deprecated/aws/templates/R80.40/utils/tap-target-and-filter.yaml new file mode 100755 index 00000000..89c60ac5 --- /dev/null +++ b/deprecated/aws/templates/R80.40/utils/tap-target-and-filter.yaml @@ -0,0 +1,68 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a traffic-mirror-filter and traffic-mirror-target (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: General Settings + Parameters: + - MirroringNetworkInterfaceId + - EnvironmentPrefix + ParameterLabels: + MirroringNetworkInterfaceId: + default: Mirroring target network interface id + EnvironmentPrefix: + default: Environment prefix for created resources +Parameters: + MirroringNetworkInterfaceId: + Description: The network interface ID to which all the traffic will be mirrored. + Type: String + AllowedPattern: '^eni-[a-z0-9]+$' + EnvironmentPrefix: + Description: The environment prefix for created resources. (optional) + Type: String + AllowedPattern: '[a-zA-Z0-9-_]*' + Default: cp-tap +Resources: + TrafficMirrorFilter: + Type: AWS::EC2::TrafficMirrorFilter + Properties: + Description: Traffic mirror filter. + Tags: + - Key: Name + Value: !Join ['-', [!Ref EnvironmentPrefix, traffic-filter]] + TrafficMirrorFilterRuleIngress: + Type: AWS::EC2::TrafficMirrorFilterRule + Properties: + Description: Traffic mirror filter rule - ingress. + DestinationCidrBlock: 0.0.0.0/0 + RuleAction: accept + RuleNumber: 100 + SourceCidrBlock: 0.0.0.0/0 + TrafficDirection: ingress + TrafficMirrorFilterId: !Ref TrafficMirrorFilter + TrafficMirrorFilterRuleEgress: + Type: AWS::EC2::TrafficMirrorFilterRule + Properties: + Description: Traffic mirror filter rule - egress. + DestinationCidrBlock: 0.0.0.0/0 + RuleAction: accept + RuleNumber: 100 + SourceCidrBlock: 0.0.0.0/0 + TrafficDirection: egress + TrafficMirrorFilterId: !Ref TrafficMirrorFilter + TrafficMirrorTarget: + Type: AWS::EC2::TrafficMirrorTarget + Properties: + Description: Traffic mirror target. + NetworkInterfaceId: !Ref MirroringNetworkInterfaceId + Tags: + - Key: Name + Value: !Join ['-', [!Ref EnvironmentPrefix, traffic-target]] +Outputs: + TrafficMirrorTargetId: + Description: Traffic mirror target id. + Value: !Ref TrafficMirrorTarget + TrafficMirrorFilterId: + Description: Traffic mirror filter id. + Value: !Ref TrafficMirrorFilter \ No newline at end of file diff --git a/deprecated/aws/templates/R80.40/utils/vpc.yaml b/deprecated/aws/templates/R80.40/utils/vpc.yaml new file mode 100755 index 00000000..e04e0832 --- /dev/null +++ b/deprecated/aws/templates/R80.40/utils/vpc.yaml @@ -0,0 +1,571 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: This template creates a Multi-AZ, multi-subnet VPC infrastructure (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Availability Zone Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - Label: + default: Network Configuration + Parameters: + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - CreatePrivateSubnets + - PrivateSubnet1CIDR + - PrivateSubnet2CIDR + - PrivateSubnet3CIDR + - PrivateSubnet4CIDR + - CreateAttachmentSubnets + - AttachmentSubnet1CIDR + - AttachmentSubnet2CIDR + - AttachmentSubnet3CIDR + - AttachmentSubnet4CIDR + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of Availability Zones + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PublicSubnet3CIDR: + default: Public subnet 3 CIDR + PublicSubnet4CIDR: + default: Public subnet 4 CIDR + CreatePrivateSubnets: + default: Create private subnets + PrivateSubnet1CIDR: + default: Private subnet 1 CIDR + PrivateSubnet2CIDR: + default: Private subnet 2 CIDR + PrivateSubnet3CIDR: + default: Private subnet 3 CIDR + PrivateSubnet4CIDR: + default: Private subnet 4 CIDR + CreateAttachmentSubnets: + default: Create Attachment subnets + AttachmentSubnet1CIDR: + default: Attachment subnet 1 CIDR + AttachmentSubnet2CIDR: + default: Attachment subnet 2 CIDR + AttachmentSubnet3CIDR: + default: Attachment subnet 3 CIDR + AttachmentSubnet4CIDR: + default: Attachment subnet 4 CIDR +Parameters: + AvailabilityZones: + Description: 'List of Availability Zones to use for the subnets in the VPC. Note: The logical order is preserved.' + Type: List + MinLength: 1 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your + selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 1 + MaxValue: 4 + VPCCIDR: + Description: CIDR block for the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for the public DMZ subnet 1 located in Availability Zone 1. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for the public DMZ subnet 2 located in Availability Zone 2. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet3CIDR: + Description: CIDR block for the public DMZ subnet 3 located in Availability Zone 3. + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet4CIDR: + Description: CIDR block for the public DMZ subnet 4 located in Availability Zone 4. + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + CreatePrivateSubnets: + Description: Set to false to create only public subnets. If false, the CIDR parameters. + for ALL private subnets will be ignored. + Type: String + Default: true + AllowedValues: + - true + - false + PrivateSubnet1CIDR: + Description: CIDR block for private subnet 1 located in Availability Zone 1. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet2CIDR: + Description: CIDR block for private subnet 2 located in Availability Zone 2. + Type: String + Default: 10.0.21.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet3CIDR: + Description: CIDR block for private subnet 3 located in Availability Zone 3. + Type: String + Default: 10.0.31.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet4CIDR: + Description: CIDR block for private subnet 4 located in Availability Zone 4. + Type: String + Default: 10.0.41.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + CreateAttachmentSubnets: + Description: Set true for creating designated subnets for VPC attachments. If false, + the CIDR parameters for the Attachment subnets will be ignored. + Type: String + Default: false + AllowedValues: + - true + - false + AttachmentSubnet1CIDR: + Description: CIDR block for Attachment subnet 1 located in Availability Zone 1. + Type: String + Default: 10.0.12.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + AttachmentSubnet2CIDR: + Description: CIDR block for Attachment subnet 2 located in Availability Zone 2. + Type: String + Default: 10.0.22.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + AttachmentSubnet3CIDR: + Description: CIDR block for Attachment subnet 3 located in Availability Zone 3. + Type: String + Default: 10.0.32.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + AttachmentSubnet4CIDR: + Description: CIDR block for Attachment subnet 4 located in Availability Zone 4. + Type: String + Default: 10.0.42.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + 2AZs: !Or [!Equals [!Ref NumberOfAZs, 2], !Condition 3AZs] + PrivateSubnets: !Equals [!Ref CreatePrivateSubnets, true] + 2AZsPrivateSubnets: !And [!Condition PrivateSubnets, !Condition 2AZs] + 3AZsPrivateSubnets: !And [!Condition PrivateSubnets, !Condition 3AZs] + 4AZsPrivateSubnets: !And [!Condition PrivateSubnets, !Condition 4AZs] + AttachmentSubnets: !Equals [!Ref CreateAttachmentSubnets, true] + 2AZsAttachmentSubnets: !And [!Condition AttachmentSubnets, !Condition 2AZs] + 3AZsAttachmentSubnets: !And [!Condition AttachmentSubnets, !Condition 3AZs] + 4AZsAttachmentSubnets: !And [!Condition AttachmentSubnets, !Condition 4AZs] +Resources: + VPC: + Type: AWS::EC2::VPC + Properties: + CidrBlock: !Ref VPCCIDR + EnableDnsSupport: true + EnableDnsHostnames: true + Tags: + - Key: Name + Value: !Ref 'AWS::StackName' + InternetGateway: + Type: AWS::EC2::InternetGateway + Properties: + Tags: + - Key: Name + Value: !Ref 'AWS::StackName' + - Key: Network + Value: Public + VPCGatewayAttachment: + Type: AWS::EC2::VPCGatewayAttachment + DependsOn: [VPC, InternetGateway] + Properties: + VpcId: !Ref VPC + InternetGatewayId: !Ref InternetGateway + PublicSubnet1: + Type: AWS::EC2::Subnet + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 1 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnet2: + Condition: 2AZs + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 2 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnet3: + Condition: 3AZs + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 3 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnet4: + Condition: 4AZs + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 4 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnetRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPC + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: Public Subnets Route Table + - Key: Network + Value: Public + PublicSubnetRoute: + DependsOn: [VPCGatewayAttachment, PublicSubnetRouteTable] + Type: AWS::EC2::Route + Properties: + RouteTableId: !Ref PublicSubnetRouteTable + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref InternetGateway + PublicSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: [PublicSubnet1, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet1 + RouteTableId: !Ref PublicSubnetRouteTable + PublicSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 2AZs + DependsOn: [PublicSubnet2, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet2 + RouteTableId: !Ref PublicSubnetRouteTable + PublicSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + DependsOn: [PublicSubnet3, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet3 + RouteTableId: !Ref PublicSubnetRouteTable + PublicSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + DependsOn: [PublicSubnet4, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet4 + RouteTableId: !Ref PublicSubnetRouteTable + PrivateSubnet1: + Type: AWS::EC2::Subnet + Condition: PrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 1 + - Key: Network + Value: Private + PrivateSubnet2: + Type: AWS::EC2::Subnet + Condition: 2AZsPrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 2 + - Key: Network + Value: Private + PrivateSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZsPrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 3 + - Key: Network + Value: Private + PrivateSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZsPrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 4 + - Key: Network + Value: Private + AttachmentSubnet1: + Condition: AttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 1 + - Key: Network + Value: Private + AttachmentSubnet2: + Condition: AttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 2 + - Key: Network + Value: Private + AttachmentSubnet3: + Condition: 3AZsAttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 3 + - Key: Network + Value: Private + AttachmentSubnet4: + Condition: 4AZsAttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 4 + - Key: Network + Value: Private +Outputs: + VPCID: + Value: !Ref VPC + Description: VPC ID. + Export: + Name: !Sub '${AWS::StackName}-VPCID' + VPCCIDR: + Value: !Ref VPCCIDR + Description: VPC CIDR + Export: + Name: !Sub '${AWS::StackName}-VPCCIDR' + PublicSubnet1CIDR: + Description: Public subnet 1 CIDR in Availability Zone 1. + Value: !Ref PublicSubnet1CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet1CIDR' + PublicSubnet1ID: + Description: Public subnet 1 ID in Availability Zone 1. + Value: !Ref PublicSubnet1 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet1ID' + PublicSubnet2CIDR: + Condition: 2AZs + Description: Public subnet 2 CIDR in Availability Zone 2. + Value: !Ref PublicSubnet2CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet2CIDR' + PublicSubnet2ID: + Condition: 2AZs + Description: Public subnet 2 ID in Availability Zone 2. + Value: !Ref PublicSubnet2 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet2ID' + PublicSubnet3CIDR: + Condition: 3AZs + Description: Public subnet 3 CIDR in Availability Zone 3. + Value: !Ref PublicSubnet3CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet3CIDR' + PublicSubnet3ID: + Condition: 3AZs + Description: Public subnet 3 ID in Availability Zone 3. + Value: !Ref PublicSubnet3 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet3ID' + PublicSubnet4CIDR: + Condition: 4AZs + Description: Public subnet 4 CIDR in Availability Zone 4. + Value: !Ref PublicSubnet4CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet4CIDR' + PublicSubnet4ID: + Condition: 4AZs + Description: Public subnet 4 ID in Availability Zone 4. + Value: !Ref PublicSubnet4 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet4ID' + PublicSubnetRouteTable: + Value: !Ref PublicSubnetRouteTable + Description: Public subnet route table. + Export: + Name: !Sub '${AWS::StackName}-PublicSubnetRouteTable' + PrivateSubnet1CIDR: + Condition: PrivateSubnets + Description: Private subnet 1 CIDR in Availability Zone 1. + Value: !Ref PrivateSubnet1CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet1CIDR' + PrivateSubnet1ID: + Condition: PrivateSubnets + Description: Private subnet 1 ID in Availability Zone 1. + Value: !Ref PrivateSubnet1 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet1ID' + PrivateSubnet2CIDR: + Condition: 2AZsPrivateSubnets + Description: Private subnet 2 CIDR in Availability Zone 2. + Value: !Ref PrivateSubnet2CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet2CIDR' + PrivateSubnet2ID: + Condition: 2AZsPrivateSubnets + Description: Private subnet 2 ID in Availability Zone 2. + Value: !Ref PrivateSubnet2 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet2ID' + PrivateSubnet3CIDR: + Condition: 3AZsPrivateSubnets + Description: Private subnet 3 CIDR in Availability Zone 3. + Value: !Ref PrivateSubnet3CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet3CIDR' + PrivateSubnet3ID: + Condition: 3AZsPrivateSubnets + Description: Private subnet 3 ID in Availability Zone 3. + Value: !Ref PrivateSubnet3 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet3ID' + PrivateSubnet4CIDR: + Condition: 4AZsPrivateSubnets + Description: Private subnet 4 CIDR in Availability Zone 4. + Value: !Ref PrivateSubnet4CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet4CIDR' + PrivateSubnet4ID: + Condition: 4AZsPrivateSubnets + Description: Private subnet 4 ID in Availability Zone 4. + Value: !Ref PrivateSubnet4 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet4ID' + AttachmentSubnet1CIDR: + Condition: AttachmentSubnets + Description: Attachment subnet 1 CIDR in Availability Zone 1. + Value: !Ref AttachmentSubnet1CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet1CIDR' + AttachmentSubnet1ID: + Condition: AttachmentSubnets + Description: Attachment subnet 1 ID in Availability Zone 1. + Value: !Ref AttachmentSubnet1 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet1ID' + AttachmentSubnet2CIDR: + Condition: 2AZsAttachmentSubnets + Description: Attachment subnet 2 CIDR in Availability Zone 2. + Value: !Ref AttachmentSubnet2CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet2CIDR' + AttachmentSubnet2ID: + Condition: 2AZsAttachmentSubnets + Description: Attachment subnet 2 ID in Availability Zone 2. + Value: !Ref AttachmentSubnet2 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet2ID' + AttachmentSubnet3CIDR: + Condition: 3AZsAttachmentSubnets + Description: Attachment subnet 3 CIDR in Availability Zone 3. + Value: !Ref AttachmentSubnet3CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet3CIDR' + AttachmentSubnet3ID: + Condition: 3AZsAttachmentSubnets + Description: Attachment subnet 3 ID in Availability Zone 3. + Value: !Ref AttachmentSubnet3 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet3ID' + AttachmentSubnet4CIDR: + Condition: 4AZsAttachmentSubnets + Description: Attachment subnet 4 CIDR in Availability Zone 4. + Value: !Ref AttachmentSubnet4CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet4CIDR' + AttachmentSubnet4ID: + Condition: 4AZsAttachmentSubnets + Description: Attachment subnet 4 ID in Availability Zone 4. + Value: !Ref AttachmentSubnet4 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet4ID' + IGWID: + Description: IGW ID. + Value: !Join ['', [!Ref InternetGateway]] + Export: + Name: !Sub '${AWS::StackName}-IGWID' \ No newline at end of file diff --git a/deprecated/aws/templates/management-r80/README.md b/deprecated/aws/templates/R80/management-r80/README.md old mode 100644 new mode 100755 similarity index 100% rename from deprecated/aws/templates/management-r80/README.md rename to deprecated/aws/templates/R80/management-r80/README.md diff --git a/deprecated/aws/templates/management-r80/r80.json b/deprecated/aws/templates/R80/management-r80/r80.json similarity index 100% rename from deprecated/aws/templates/management-r80/r80.json rename to deprecated/aws/templates/R80/management-r80/r80.json diff --git a/deprecated/aws/templates/R81/autoscale/autoscale.yaml b/deprecated/aws/templates/R81/autoscale/autoscale.yaml new file mode 100755 index 00000000..28f3a637 --- /dev/null +++ b/deprecated/aws/templates/R81/autoscale/autoscale.yaml @@ -0,0 +1,612 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Create an Auto Scaling group of Check Point gateways (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - GatewaysSubnets + - Label: + default: EC2 Instances Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - VolumeSize + - VolumeType + - EnableVolumeEncryption + - EnableInstanceConnect + - MetaDataToken + - Label: + default: Auto Scaling Configuration + Parameters: + - GatewaysMinSize + - GatewaysMaxSize + - AdminEmail + - GatewaysTargetGroups + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - Label: + default: Automatic Provisioning with Security Management Server Settings + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + - Label: + default: Proxy Configuration (optional) + Parameters: + - ELBType + - ELBPort + - ELBClients + ParameterLabels: + VPC: + default: VPC + GatewaysSubnets: + default: Gateways subnets + GatewayName: + default: Gateways name + GatewayInstanceType: + default: Gateways instance type + KeyName: + default: Key name + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableVolumeEncryption: + default: Enable volume encryption + EnableInstanceConnect: + default: Enable AWS Instance Connect + MetaDataToken: + default: Metadata HTTP token + GatewaysMinSize: + default: Minimum Gateway group size + GatewaysMaxSize: + default: Maximum Gateway group size + AdminEmail: + default: Email address + GatewaysTargetGroups: + default: Gateways target groups + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Gateways Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: Gateways SIC key + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Gateways bootstrap script + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template + ELBType: + default: Proxy type + ELBPort: + default: Proxy port + ELBClients: + default: Allowed proxy clients +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + GatewaysSubnets: + Description: Select at least 2 public subnets in the VPC. + Type: List + MinLength: 2 + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The instance type of the Secutiry Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableVolumeEncryption: + Description: Encrypt Auto Scaling instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewaysMinSize: + Description: The minimal number of gateways in the Auto Scaling group. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of gateways in the Auto Scaling group. + Type: Number + Default: 10 + MinValue: 1 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + ConstraintDescription: Must be a valid email address. + GatewaysTargetGroups: + Description: A list of Target Groups to associate with the Auto Scaling. + group (comma separated list of ARNs, without spaces) (optional) + Type: String + Default: '' + GatewayVersion: + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD". + to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections. + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: ASG-configuration + MinLength: 1 + MaxLength: 30 + ELBType: + Type: String + Default: none + AllowedValues: + - none + - internal + - internet-facing + ELBPort: + Type: Number + Default: 8080 + ELBClients: + Type: String + Default: 0.0.0.0/0 + AllowedPattern: '^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})/(\d{1,2})$' +Conditions: + ProvidedAdminEmail: !Not [!Equals [!Ref AdminEmail, '']] + ProvidedTargetGroups: !Not [!Equals [!Ref GatewaysTargetGroups, '']] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + CreateELB: !Not [!Equals [!Ref ELBType, none]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ChkpGatewayRole: + Type: AWS::IAM::Role + Condition: EnableCloudWatch + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: + - ec2.amazonaws.com + Action: + - sts:AssumeRole + Path: / + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: ChkpGatewayPolicy + PolicyRole: !Ref ChkpGatewayRole + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: EnableCloudWatch + Properties: + Path: / + Roles: + - !Ref ChkpGatewayRole + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion, GW]] + NotificationTopic: + Type: AWS::SNS::Topic + Condition: ProvidedAdminEmail + Properties: + Subscription: + - Endpoint: !Ref AdminEmail + Protocol: email + ElasticLoadBalancer: + Type: AWS::ElasticLoadBalancing::LoadBalancer + Condition: CreateELB + Properties: + CrossZone: true + Listeners: + - LoadBalancerPort: !Ref ELBPort + InstancePort: !Ref ELBPort + Protocol: TCP + HealthCheck: + Target: !Join [':', [TCP, !Ref ELBPort]] + HealthyThreshold: 3 + UnhealthyThreshold: 5 + Interval: 30 + Timeout: 5 + Scheme: !Ref ELBType + Subnets: !Ref GatewaysSubnets + Policies: + - PolicyName: EnableProxyProtocol + PolicyType: ProxyProtocolPolicyType + Attributes: + - Name: ProxyProtocol + Value: true + InstancePorts: + - !Ref ELBPort + SecurityGroups: + - !Ref ELBSecurityGroup + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + Tags: + - Key: Name + Value: !Join ['_', [!Ref 'AWS::StackName', PermissiveSecurityGroup]] + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + GatewayGroup: + Type: AWS::AutoScaling::AutoScalingGroup + DependsOn: GatewayLaunchTemplate + Properties: + VPCZoneIdentifier: !Ref GatewaysSubnets + LaunchTemplate: + LaunchTemplateId: !Ref GatewayLaunchTemplate + Version: !GetAtt GatewayLaunchTemplate.LatestVersionNumber + MinSize: !Ref GatewaysMinSize + MaxSize: !Ref GatewaysMaxSize + LoadBalancerNames: !If [CreateELB, [!Ref ElasticLoadBalancer], !Ref 'AWS::NoValue'] + TargetGroupARNs: !If [ProvidedTargetGroups, !Split [',', !Ref GatewaysTargetGroups], !Ref 'AWS::NoValue'] + HealthCheckType: ELB + HealthCheckGracePeriod: 3600 + NotificationConfiguration: !If + - ProvidedAdminEmail + - TopicARN: !Ref NotificationTopic + NotificationTypes: + - autoscaling:EC2_INSTANCE_LAUNCH + - autoscaling:EC2_INSTANCE_LAUNCH_ERROR + - autoscaling:EC2_INSTANCE_TERMINATE + - autoscaling:EC2_INSTANCE_TERMINATE_ERROR + - !Ref 'AWS::NoValue' + Tags: + - Key: Name + Value: !Ref GatewayName + PropagateAtLaunch: true + - Key: x-chkp-tags + Value: !Join + - ':' + - - !Join ['=', [management, !Ref ManagementServer]] + - !Join ['=', [template, !Ref ConfigurationTemplate]] + - !Join ['=', [ip-address, !Ref ControlGatewayOverPrivateOrPublicAddress]] + PropagateAtLaunch: true + GatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: true + Groups: + - !Ref PermissiveSecurityGroup + Monitoring: + Enabled: true + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [EnableCloudWatch, !Ref InstanceProfile, !Ref 'AWS::NoValue'] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect}' + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" sicKey=\"${sic}\" installationType=\"autoscale\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"autoscale\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + GatewayScaleUpPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref GatewayGroup + Cooldown: 300 + ScalingAdjustment: 1 + GatewayScaleDownPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref GatewayGroup + Cooldown: 300 + ScalingAdjustment: -1 + CPUAlarmHigh: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-up if CPU > 80% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 80 + AlarmActions: + - !Ref GatewayScaleUpPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref GatewayGroup + ComparisonOperator: GreaterThanThreshold + CPUAlarmLow: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-down if CPU < 60% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 60 + AlarmActions: + - !Ref GatewayScaleDownPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref GatewayGroup + ComparisonOperator: LessThanThreshold + ELBSecurityGroup: + Type: AWS::EC2::SecurityGroup + Condition: CreateELB + Properties: + GroupDescription: ELB security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: tcp + CidrIp: !Ref ELBClients + FromPort: !Ref ELBPort + ToPort: !Ref ELBPort +Outputs: + URL: + Description: The URL of the Proxy. + Condition: CreateELB + Value: !Join ['', ['http://', !GetAtt ElasticLoadBalancer.DNSName]] + SecurityGroup: + Description: The Security Group of the Auto Scaling group. + Value: !GetAtt PermissiveSecurityGroup.GroupId + diff --git a/deprecated/aws/templates/R81/autoscale/custom-autoscale.yaml b/deprecated/aws/templates/R81/autoscale/custom-autoscale.yaml new file mode 100755 index 00000000..70782d13 --- /dev/null +++ b/deprecated/aws/templates/R81/autoscale/custom-autoscale.yaml @@ -0,0 +1,226 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Create an Auto Scaling group of workload servers (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - ServersSubnets + - Label: + default: EC2 Instances Configuration + Parameters: + - ServerAMI + - ServerName + - ServerInstanceType + - KeyName + - AllocatePublicAddress + - Label: + default: Auto Scaling Configuration + Parameters: + - ServersMinSize + - ServersMaxSize + - AdminEmail + - ServersTargetGroups + - SourceSecurityGroup + ParameterLabels: + VPC: + default: VPC + ServersSubnets: + default: Servers subnets + ServerAMI: + default: Amazon Image ID + ServerName: + default: Instance Name + ServerInstanceType: + default: Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + ServersMinSize: + default: Minimum group size + ServerMaxSize: + default: Maximum group size + AdminEmail: + default: Email address + ServersTargetGroups: + default: Target Groups + SourceSecurityGroup: + default: Source Security Group +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ServersSubnets: + Description: Select at least 2 subnets in the VPC. + Type: List + MinLength: 2 + ServerAMI: + Description: AMI of the servers. + Type: String + AllowedPattern: '^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$' + ConstraintDescription: Must be a valid Amazon Machine Image ID. + ServerName: + Description: The servers name tag. + Type: String + Default: Server + ServerInstanceType: + Description: The instance type of the servers. + Type: String + Default: t3.micro + AllowedValues: + - t3.nano + - t3.micro + - t3.small + - t3.medium + - t3.large + - t3.xlarge + - t3.2xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an elastic IP for each server. + Type: String + Default: false + AllowedValues: + - true + - false + ServersMinSize: + Description: The minimal number of servers in the Auto Scaling group. + Type: Number + Default: 2 + MinValue: 1 + ServersMaxSize: + Description: The maximal number of servers in the Auto Scaling group. + Type: Number + Default: 10 + MinValue: 1 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. + (optional) + Type: String + Default: '' + AllowedPattern: '(|([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))' + ConstraintDescription: Must be a valid email address. + ServersTargetGroups: + Description: An optional list of Target Groups to associate with the Auto Scaling group (comma separated list of ARNs, without spaces). + Type: String + Default: '' + SourceSecurityGroup: + Description: The ID of Security Group from which access will be allowed to the instances in this Auto Scaling group. + Type: String + Default: '' +Conditions: + ProvidedAdminEmail: !Not [!Equals [!Ref AdminEmail, '']] + ProvidedTargetGroups: !Not [!Equals [!Ref ServersTargetGroups, '']] + NotProvidedSecurityGroup: !Equals [!Ref SourceSecurityGroup, ''] +Resources: + NotificationTopic: + Type: AWS::SNS::Topic + Condition: ProvidedAdminEmail + Properties: + Subscription: + - Endpoint: !Ref AdminEmail + Protocol: email + ServersSecurityGroup: + Type: AWS::EC2::SecurityGroup + Condition: NotProvidedSecurityGroup + Properties: + Tags: + - Key: Name + Value: !Join ['_', [!Ref 'AWS::StackName', ServersSecurityGroup]] + GroupDescription: Servers security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + ServersLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: !Ref AllocatePublicAddress + Groups: !If [NotProvidedSecurityGroup, [!Ref ServersSecurityGroup], [!Ref SourceSecurityGroup]] + Monitoring: + Enabled: true + KeyName: !Ref KeyName + ImageId: !Ref ServerAMI + InstanceType: !Ref ServerInstanceType + VersionDescription: Initial template version + ServersGroup: + Type: AWS::AutoScaling::AutoScalingGroup + Properties: + VPCZoneIdentifier: !Ref ServersSubnets + LaunchTemplate: + LaunchTemplateId: !Ref ServersLaunchTemplate + Version: !GetAtt ServersLaunchTemplate.LatestVersionNumber + MinSize: !Ref ServersMinSize + MaxSize: !Ref ServersMaxSize + TargetGroupARNs: !If [ProvidedTargetGroups, !Split [',', !Ref ServersTargetGroups], !Ref 'AWS::NoValue'] + NotificationConfiguration: !If + - ProvidedAdminEmail + - TopicARN: !Ref NotificationTopic + NotificationTypes: + - autoscaling:EC2_INSTANCE_LAUNCH + - autoscaling:EC2_INSTANCE_LAUNCH_ERROR + - autoscaling:EC2_INSTANCE_TERMINATE + - autoscaling:EC2_INSTANCE_TERMINATE_ERROR + - !Ref 'AWS::NoValue' + Tags: + - Key: Name + Value: !Ref ServerName + PropagateAtLaunch: true + ScaleUpPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref ServersGroup + Cooldown: 300 + ScalingAdjustment: 1 + ScaleDownPolicy: + Type: AWS::AutoScaling::ScalingPolicy + Properties: + AdjustmentType: ChangeInCapacity + AutoScalingGroupName: !Ref ServersGroup + Cooldown: 300 + ScalingAdjustment: -1 + CPUAlarmHigh: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-up if CPU > 80% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 80 + AlarmActions: + - !Ref ScaleUpPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref ServersGroup + ComparisonOperator: GreaterThanThreshold + CPUAlarmLow: + Type: AWS::CloudWatch::Alarm + Properties: + AlarmDescription: Scale-down if CPU < 60% for 10 minutes. + MetricName: CPUUtilization + Namespace: AWS/EC2 + Statistic: Average + Period: 300 + EvaluationPeriods: 2 + Threshold: 60 + AlarmActions: + - !Ref ScaleDownPolicy + Dimensions: + - Name: AutoScalingGroupName + Value: !Ref ServersGroup + ComparisonOperator: LessThanThreshold diff --git a/deprecated/aws/templates/R81/autoscale/tgw-asg-master.yaml b/deprecated/aws/templates/R81/autoscale/tgw-asg-master.yaml new file mode 100755 index 00000000..43033b4a --- /dev/null +++ b/deprecated/aws/templates/R81/autoscale/tgw-asg-master.yaml @@ -0,0 +1,690 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Network Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - CloudWatch + - ASN + - AdminEmail + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - ManagementPermissions + - ManagementPredefinedRole + - GatewaysBlades + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + - Label: + default: Automatic Provisioning with Security Management Server Settings + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of AZs + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public Subnet 1 + PublicSubnet2CIDR: + default: Public Subnet 2 + PublicSubnet3CIDR: + default: Public Subnet 3 + PublicSubnet4CIDR: + default: Public Subnet 4 + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + GatewayName: + default: GatewayName + GatewayInstanceType: + default: Gateways instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Gateways version & license + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + CloudWatch: + default: CloudWatch metrics + ASN: + default: BGP ASN + AdminEmail: + default: Email address + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Instance type + ManagementVersion: + default: Version & license + ManagementPasswordHash: + default: Password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + ManagementPermissions: + default: IAM role + ManagementPredefinedRole: + default: Existing IAM role name + GatewaysBlades: + default: Default Blades + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Manage Gateways + GatewaysAddresses: + default: Gateways addresses + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + AvailabilityZones: + Description: List of Availability Zones (AZs) to use for the subnets in the VPC. Select at least two. + Type: List + MinLength: 2 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 2 + MaxValue: 4 + VPCCIDR: + Description: CIDR block for the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. If you choose to deploy a Security Management Server it will be deployed in this subnet. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet3CIDR: + Description: CIDR block for public subnet 3 located in the 3rd Availability Zone. + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet4CIDR: + Description: CIDR block for public subnet 4 located in the 4th Availability Zone. + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + ASN: + Description: The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways. + Type: String + AllowedPattern: '^[0-9]+$' + Default: 65000 + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + ConstraintDescription: Must be a valid email address. + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The version and license to install on the Security Management Server. + Type: String + Default: R81.20-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG + - R81.10-BYOL + - R81.10-PAYG + - R81.20-BYOL + - R81.20-PAYG + - R82-BYOL + - R82-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read-write permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + ManagementPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'. + Type: String + Default: '' + GatewaysBlades: + Description: Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (these and additional Blades can be manually turned on or off later). + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^$|^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: TGW-ASG-configuration + MinLength: 1 + MaxLength: 30 +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + DeployManagement: !Equals [!Ref ManagementDeploy, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: !Ref NumberOfAZs + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PublicSubnet3CIDR: !Ref PublicSubnet3CIDR + PublicSubnet4CIDR: !Ref PublicSubnet4CIDR + CreatePrivateSubnets: false + MainStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/autoscale/tgw-asg.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + GatewaysSubnets: !Join + - ',' + - - !GetAtt VPCStack.Outputs.PublicSubnet1ID + - !GetAtt VPCStack.Outputs.PublicSubnet2ID + - !If [3AZs, !GetAtt VPCStack.Outputs.PublicSubnet3ID, !Ref 'AWS::NoValue'] + - !If [4AZs, !GetAtt VPCStack.Outputs.PublicSubnet4ID, !Ref 'AWS::NoValue'] + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + AllowUploadDownload: !Ref AllowUploadDownload + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + CloudWatch: !Ref CloudWatch + ASN: !Ref ASN + AdminEmail: !Ref AdminEmail + ManagementDeploy: !Ref ManagementDeploy + ManagementInstanceType: !Ref ManagementInstanceType + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + ManagementPermissions: !Ref ManagementPermissions + ManagementPredefinedRole: !Ref ManagementPredefinedRole + GatewaysBlades: !Ref GatewaysBlades + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate +Outputs: + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !Ref ConfigurationTemplate + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name. + Value: !GetAtt MainStack.Outputs.ControllerName + ManagementPublicAddress: + Description: The public address of the management servers. + Value: !GetAtt MainStack.Outputs.ManagementPublicAddress + Condition: DeployManagement +Rules: + GatewayAddressRule: + RuleCondition: !Equals [!Ref ManagementDeploy, 'true'] + Assertions: + - AssertDescription: "Gateway's netowrk to communicate with the Security Management Server must be provided" + Assert: !Not [ !Equals [!Ref GatewaysAddresses, '']] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/autoscale/tgw-asg.yaml b/deprecated/aws/templates/R81/autoscale/tgw-asg.yaml new file mode 100755 index 00000000..3d196a90 --- /dev/null +++ b/deprecated/aws/templates/R81/autoscale/tgw-asg.yaml @@ -0,0 +1,682 @@ +AWSTemplateFormatVersion: '2010-09-09' +Description: Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Network Configuration + Parameters: + - VPC + - GatewaysSubnets + - Label: + default: General Settings + Parameters: + - KeyName + - EnableVolumeEncryption + - VolumeSize + - VolumeType + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - AllowUploadDownload + - Label: + default: Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - GatewaysMinSize + - GatewaysMaxSize + - GatewayVersion + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - CloudWatch + - ASN + - AdminEmail + - Label: + default: Check Point CloudGuard IaaS Security Management Server Configuration + Parameters: + - ManagementDeploy + - ManagementInstanceType + - ManagementVersion + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - ManagementPermissions + - ManagementPredefinedRole + - GatewaysBlades + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + - Label: + default: Automatic Provisioning with Security Management Server Settings + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + VPC: + default: VPC + GatewaysSubnets: + default: Subnets + KeyName: + default: Key name + EnableVolumeEncryption: + default: Enable environment volume encryption + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + AllowUploadDownload: + default: Allow upload & download + GatewayName: + default: Name + GatewayInstanceType: + default: Instance type + GatewaysMinSize: + default: Minimum group size + GatewaysMaxSize: + default: Maximum group size + GatewayVersion: + default: Version & license + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + CloudWatch: + default: CloudWatch metrics + ASN: + default: BGP ASN + AdminEmail: + default: Email address + ManagementDeploy: + default: Deploy Management Server + ManagementInstanceType: + default: Instance type + ManagementVersion: + default: Version & license + ManagementPasswordHash: + default: Password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + ManagementPermissions: + default: IAM role + ManagementPredefinedRole: + default: Existing IAM role name + GatewaysBlades: + default: Default Blades + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses + GatewayManagement: + default: Manage Gateways + ControlGatewayOverPrivateOrPublicAddress: + default: Gateways addresses + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: You must select a VPC. + GatewaysSubnets: + Description: Select at least 2 external subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet. + Type: List + MinLength: 2 + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instances created by this stack. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: Must be the name of an existing EC2 KeyPair. + EnableVolumeEncryption: + Description: Encrypt Environment instances volume with default AWS KMS key. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The EC2 instance type for the Security Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + GatewaysMinSize: + Description: The minimal number of Security Gateways. + Type: Number + Default: 2 + MinValue: 1 + GatewaysMaxSize: + Description: The maximal number of Security Gateways. + Type: Number + Default: 10 + MinValue: 1 + GatewayVersion: + Description: The version and license to install on the Security Gateways. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + ConstraintDescription: Secure Internal Communication activation key should contain only alpha numeric characters and be at least 8 characters long. + NoEcho: true + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + ASN: + Description: The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways. + Type: String + Default: 65000 + AllowedPattern: '^[0-9]+$' + AdminEmail: + Description: Notifications about scaling events will be sent to this email address. (optional) + Type: String + Default: '' + AllowedPattern: '^(([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?))?$' + ConstraintDescription: Must be a valid email address. + ManagementDeploy: + Description: Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementInstanceType: + Description: The EC2 instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ManagementVersion: + Description: The version and license to install on the Security Management Server. + Type: String + Default: R81.20-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG + - R81.10-BYOL + - R81.10-PAYG + - R81.20-BYOL + - R81.20-PAYG + - R82-BYOL + - R82-PAYG + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read-write permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + ManagementPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'. + Type: String + Default: '' + GatewaysBlades: + Description: Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (these and additional Blades can be manually turned on or off later). + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Security Management Server. + Type: String + AllowedPattern: '^$|^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the gateways are provisioned using their private or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic provisioning configuration. + Type: String + Default: management-server + MinLength: 1 + ConfigurationTemplate: + Description: A name of a gateway configuration template in the automatic provisioning configuration. + Type: String + Default: TGW-ASG-configuration + MinLength: 1 + MaxLength: 30 +Conditions: + VolumeEncryption: !Equals [!Ref EnableVolumeEncryption, true] + DeployManagement: !Equals [!Ref ManagementDeploy, true] +Resources: + ManagementStack: + Type: AWS::CloudFormation::Stack + Condition: DeployManagement + Properties: + TemplateURL: __URL__/management/management.yaml + Parameters: + VPC: !Ref VPC + ManagementSubnet: !Select [0, !Ref GatewaysSubnets] + ManagementName: !Ref ManagementServer + ManagementInstanceType: !Ref ManagementInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: true + VolumeEncryption: !If [VolumeEncryption, alias/aws/ebs, ''] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + ManagementPermissions: !Ref ManagementPermissions + ManagementPredefinedRole: !Ref ManagementPredefinedRole + ManagementVersion: !Ref ManagementVersion + ManagementPasswordHash: !Ref ManagementPasswordHash + ManagementMaintenancePasswordHash: !Ref ManagementMaintenancePasswordHash + AllowUploadDownload: !Ref AllowUploadDownload + AdminCIDR: !Ref AdminCIDR + GatewayManagement: !Ref GatewayManagement + GatewaysAddresses: !Ref GatewaysAddresses + ManagementBootstrapScript: !Join + - ';' + - - 'echo -e "\nStarting Bootstrap script\n"' + - 'echo "Setting up bootstrap parameters"' + - !Sub 'conf_template=${ConfigurationTemplate} ; mgmt=${ManagementServer} ; region=${AWS::Region} ; blades=${GatewaysBlades}' + - !Sub ['version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - !Join ['', ['sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ' | base64 -d)"']] + - 'community="tgw-community" ; controller="tgw-controller"' + - 'echo "Adding tgw identifier to cloud-version"' + - 'template="management_tgw_asg"' + - 'cv_path="/etc/cloud-version"' + - 'if test -f ${cv_path}; then sed -i ''/template_name/c\template_name: ''"${template}"'''' /etc/cloud-version; fi' + - 'cv_json_path="/etc/cloud-version.json"' + - 'cv_json_path_tmp="/etc/cloud-version-tmp.json"' + - 'if test -f ${cv_json_path}; then cat ${cv_json_path} | jq ''.template_name = "''"${template}"''"'' > ${cv_json_path_tmp}; mv ${cv_json_path_tmp} ${cv_json_path}; fi' + - 'echo "Configuring VPN community: ${community}"' + - '[[ -d /opt/CPcme/menu/additions ]] && /opt/CPcme/menu/additions/config-community.sh "${community}" || /etc/fw/scripts/autoprovision/config-community.sh "${community}"' + - 'echo "Setting VPN rules"' + - 'mgmt_cli -r true add access-layer name "Inline"' + - 'mgmt_cli -r true add access-rule layer Network position 1 name "${community} VPN Traffic Rule" vpn.directional.1.from "${community}" vpn.directional.1.to "${community}" vpn.directional.2.from "${community}" vpn.directional.2.to External_clear action "Apply Layer" source "Any" destination "Any" service "Any" inline-layer "Inline"' + - 'mgmt_cli -r true add dynamic-object name "LocalGateway"' + - 'mgmt_cli -r true add nat-rule package standard position bottom install-on "Policy Targets" original-source All_Internet translated-source "LocalGateway" method hide' + - 'echo "Setting CME configurations"' + - 'autoprov_cfg -f init AWS -mn "${mgmt}" -tn "${conf_template}" -cn "${controller}" -po Standard -otp "${sic}" -r "${region}" -ver "${version}" -iam -dt TGW' + - 'autoprov_cfg -f set controller AWS -cn "${controller}" -sv -com "${community}"' + - 'autoprov_cfg -f set template -tn "${conf_template}" -vpn -vd "" -con "${community}"' + - '${blades} && autoprov_cfg -f set template -tn "${conf_template}" -ia -ips -appi -av -ab' + - 'echo -e "\nFinished Bootstrap script\n"' + SecurityGatewaysStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/autoscale/autoscale.yaml + Parameters: + VPC: !Ref VPC + GatewaysSubnets: !Join [',', !Ref GatewaysSubnets] + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + EnableVolumeEncryption: !Ref EnableVolumeEncryption + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + EnableInstanceConnect: !Ref EnableInstanceConnect + MetaDataToken: !Ref MetaDataToken + GatewaysMinSize: !Ref GatewaysMinSize + GatewaysMaxSize: !Ref GatewaysMaxSize + AdminEmail: !Ref AdminEmail + GatewayVersion: !Ref GatewayVersion + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Join + - ';' + - - 'echo -e "\nStarting Bootstrap script\n"' + - 'echo "Setting up bootstrap parameters"' + - !Sub 'asn=${ASN}' + - 'echo "Adding tgw identifier to cloud-version"' + - 'template="autoscale_tgw"' + - 'cv_path="/etc/cloud-version"' + - 'if test -f ${cv_path}; then sed -i ''/template_name/c\template_name: ''"${template}"'''' /etc/cloud-version; fi' + - 'cv_json_path="/etc/cloud-version.json"' + - 'cv_json_path_tmp="/etc/cloud-version-tmp.json"' + - 'if test -f ${cv_json_path}; then cat ${cv_json_path} | jq ''.template_name = "''"${template}"''"'' > ${cv_json_path_tmp}; mv ${cv_json_path_tmp} ${cv_json_path}; fi' + - 'echo "Setting ASN to: ${asn}"' + - 'clish -c "set as ${asn}" -s' + - 'echo -e "\nFinished Bootstrap script\n"' + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate +Outputs: + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name. + Value: !Ref ConfigurationTemplate + ControllerName: + Description: The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name. + Value: tgw-controller + ManagementPublicAddress: + Description: The public address of the management servers. + Value: !GetAtt ManagementStack.Outputs.PublicAddress + Condition: DeployManagement +Rules: + GatewayAddressRule: + RuleCondition: !Equals [!Ref ManagementDeploy, 'true'] + Assertions: + - AssertDescription: "Gateway's netowrk to communicate with the Security Management Server must be provided" + Assert: !Not [ !Equals [!Ref GatewaysAddresses, '']] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/cluster/cluster-master.yaml b/deprecated/aws/templates/R81/cluster/cluster-master.yaml new file mode 100755 index 00000000..db6a1b89 --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/cluster-master.yaml @@ -0,0 +1,512 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Check Point Cluster in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZone + - VPCCIDR + - PublicSubnetCIDR + - PrivateSubnetCIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPCCIDR: + default: VPC CIDR + AvailabilityZone: + default: Availability zone + PublicSubnetCIDR: + default: Public subnet CIDR + PrivateSubnetCIDR: + default: Private subnet CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + AvailabilityZone: + Description: The availability zone in which to deploy the cluster. + Type: AWS::EC2::AvailabilityZone::Name + MinLength: 1 + VPCCIDR: + Description: The CIDR block for your VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnetCIDR: + Description: The external subnet of the cluster. The cluster's public IPs will be generated from this subnet. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnetCIDR: + Description: The internal subnet of the cluster. The cluster's private IPs will be generated from this subnet. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Default: false + Type: String + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD". + to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections. + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources (optional). + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Ref AvailabilityZone + NumberOfAZs: 1 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnetCIDR + PrivateSubnet1CIDR: !Ref PrivateSubnetCIDR + InternalRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPCStack + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: Private Subnets Route Table + ClusterStack: + Type: AWS::CloudFormation::Stack + DependsOn: VPCStack + Properties: + TemplateURL: __URL__/cluster/cluster.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnet: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PrivateSubnet: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary +Outputs: + ClusterPublicAddress: + Description: The public address of the cluster. + Value: !GetAtt ClusterStack.Outputs.ClusterPublicAddress + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberAExternalInterface: + Condition: AllocateAddress + Description: The external interface of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAExternalInterface + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateExternalAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateInternalAddress + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateExternalAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateInternalAddress + ClusterPrivateAliasExternalAddress: + Description: The secondary external private IP address of the cluster. + Value: !GetAtt ClusterStack.Outputs.ClusterPrivateAliasExternalAddress + ClusterPrivateAliasInternalAddress: + Description: The secondary internal private IP address of the cluster. + Value: !GetAtt ClusterStack.Outputs.ClusterPrivateAliasInternalAddress +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/cluster/cluster.yaml b/deprecated/aws/templates/R81/cluster/cluster.yaml new file mode 100755 index 00000000..d47be332 --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/cluster.yaml @@ -0,0 +1,762 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Cluster into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnet + - PrivateSubnet + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnet: + default: Public subnet + PrivateSubnet: + default: Private subnet + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + PublicSubnet: + Description: The public subnet of the cluster. The cluster's public IPs will be generated from this subnet. The subnet's route table must have 0.0.0.0/0 route to Internet Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + PrivateSubnet: + Description: The private subnet of the cluster. The cluster's private IPs will be generated from this subnet. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + InternalRouteTable: + Description: The route table id in which to set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the route table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD". + to get the PASSWORD's hash) (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections. + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources (optional). + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Improve product experience by sending data to Check Point + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + CreateRole: !Equals [!Ref GatewayPredefinedRole, ''] + ProvidedPassHash: !Not [!Equals [!Ref GatewayPasswordHash, '']] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + EmptyHostName: !Equals [!Ref GatewayHostname, ''] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ClusterReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ClusterReadyCondition: + Type: AWS::CloudFormation::WaitCondition + DependsOn: [MemberAInstance, MemberBInstance] + Condition: AllocateAddress + Properties: + Count: 2 + Handle: !Ref ClusterReadyHandle + Timeout: 1800 + ClusterRole: + Condition: CreateRole + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cluster-iam-role.yaml + ClusterInstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [!If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole]] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + PolicyRole: !If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole] + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join [-, [!Ref GatewayVersion, GW]] + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + MemberAExternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member A external. + SecondaryPrivateIpAddressCount: 1 + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_ExternalInterface + MemberBExternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member B external. + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_ExternalInterface + MemberAInternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member A internal. + SecondaryPrivateIpAddressCount: 1 + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_InternalInterface + MemberBInternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member B internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnet + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_InternalInterface + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + DependsOn: MemberAInternalInterface + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref MemberAInternalInterface + RouteTableId: !Ref InternalRouteTable + PrivateSubnetRouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnet + MemberAInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberAExternalInterface, MemberAInternalInterface, MemberAGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberAGatewayLaunchTemplate + Version: !GetAtt MemberAGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-A]] + - Key: x-chkp-member-ips + Value: !Join + - ':' + - - !Join [ '=', [ public-ip, !If [ AllocateAddress, !Ref MemberAPublicAddress, '' ] ] ] + - !Join [ '=', [ external-private-ip, !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress ] ] + - !Join [ '=', [ internal-private-ip, !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress ] ] + - Key: x-chkp-cluster-ips + Value: !Join + - ':' + - - !Join [ '=', [ cluster-ip, !Ref ClusterPublicAddress ] ] + - !Join [ '=', [ cluster-eth0-private-ip, !Select [ 0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses ] ] ] + - !Join [ '=', [ cluster-eth1-private-ip, !Select [ 0, !GetAtt MemberAInternalInterface.SecondaryPrivateIpAddresses ] ] ] + MemberBInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberBExternalInterface, MemberBInternalInterface, MemberBGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberBGatewayLaunchTemplate + Version: !GetAtt MemberBGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-B]] + - Key: x-chkp-member-ips + Value: !Join + - ':' + - - !Join [ '=', [ public-ip, !If [ AllocateAddress, !Ref MemberBPublicAddress, '' ] ] ] + - !Join [ '=', [ external-private-ip, !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress ] ] + - !Join [ '=', [ internal-private-ip, !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress ] ] + - Key: x-chkp-cluster-ips + Value: !Join + - ':' + - - !Join [ '=', [ cluster-ip, !Ref ClusterPublicAddress ] ] + - !Join [ '=', [ cluster-eth0-private-ip, !Select [ 0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses ] ] ] + - !Join [ '=', [ cluster-eth1-private-ip, !Select [ 0, !GetAtt MemberAInternalInterface.SecondaryPrivateIpAddresses ] ] ] + MemberAGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberAExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberAInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenA=''${MemberAToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-a'] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberAPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenA}\"" installationType=\"cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + MemberBGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberBExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberBInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenB=''${MemberBToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-b'] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberBPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenB}\"" installationType=\"cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + ClusterPublicAddress: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + MemberAPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + MemberBPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + ClusterAddressAssoc: + Type: AWS::EC2::EIPAssociation + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt ClusterPublicAddress.AllocationId + PrivateIpAddress: !Select [0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses] + MemberAAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt MemberAPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberBAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberBInstance + Properties: + NetworkInterfaceId: !Ref MemberBExternalInterface + AllocationId: !GetAtt MemberBPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress +Outputs: + ClusterPublicAddress: + Description: The public address of the cluster. + Value: !Ref ClusterPublicAddress + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !Ref MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberAPublicAddress]] + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !Join ['', ['https://', !Ref MemberAPublicAddress]] + MemberAExternalInterface: + Condition: AllocateAddress + Description: The external interface of member A. + Value: !Ref MemberAExternalInterface + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !Ref MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberBPublicAddress]] + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !Join ['', ['https://', !Ref MemberBPublicAddress]] + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress + ClusterPrivateAliasExternalAddress: + Description: The secondary external private IP address of the cluster. + Value: !Select [ 0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses ] + ClusterPrivateAliasInternalAddress: + Description: The secondary internal private IP address of the cluster. + Value: !Select [ 0, !GetAtt MemberAInternalInterface.SecondaryPrivateIpAddresses ] + +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [[!Ref MemberBToken], !Ref MemberAToken] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] + + diff --git a/deprecated/aws/templates/R81/cluster/cross-az-cluster.yaml b/deprecated/aws/templates/R81/cluster/cross-az-cluster.yaml new file mode 100755 index 00000000..fcbe2bf4 --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/cross-az-cluster.yaml @@ -0,0 +1,775 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Cluster into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnetA + - PublicSubnetB + - PrivateSubnetA + - PrivateSubnetB + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnetA: + default: Public subnet 1 + PublicSubnetB: + default: Public subnet 2 + PrivateSubnetA: + default: Private subnet 1 + PrivateSubnetB: + default: Private subnet 2 + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + PublicSubnetA: + Description: Select a public subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the first Security Gateway. + PublicSubnetB: + Description: Select a public subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the second Security Gateway. + PrivateSubnetA: + Description: Select a private subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the first Security Gateway. + PrivateSubnetB: + Description: Select a private subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the second Security Gateway. + InternalRouteTable: + Description: Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the Route Table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R81.20-BYOL + AllowedValues: + - R81.20-BYOL + - R81.20-PAYG-NGTP + - R81.20-PAYG-NGTX + - R82-BYOL + - R82-PAYG-NGTP + - R82-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose + Improve product experience by sending data to Check Point. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + CreateRole: !Equals [!Ref GatewayPredefinedRole, ''] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + EmptyHostName: !Equals [!Ref GatewayHostname, ''] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ClusterReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ClusterReadyCondition: + Type: AWS::CloudFormation::WaitCondition + DependsOn: [MemberAInstance, MemberBInstance] + Condition: AllocateAddress + Properties: + Count: 2 + Handle: !Ref ClusterReadyHandle + Timeout: 1800 + ClusterRole: + Condition: CreateRole + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cluster-iam-role.yaml + ClusterInstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [!If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole]] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName' ] + PolicyRole: !If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole] + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion, GW]] + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + MemberAExternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member A external. + SecondaryPrivateIpAddressCount: 1 + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnetA + Tags: + - Key: x-chkp-interface-type + Value: external + MemberBExternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member B external. + SecondaryPrivateIpAddressCount: 1 + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnetB + Tags: + - Key: x-chkp-interface-type + Value: external + MemberAInternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member A internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnetA + Tags: + - Key: x-chkp-interface-type + Value: internal + MemberBInternalInterface: + Type: AWS::EC2::NetworkInterface + DependsOn: PermissiveSecurityGroup + Properties: + Description: Member B internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnetB + Tags: + - Key: x-chkp-interface-type + Value: internal + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + DependsOn: MemberAInternalInterface + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref MemberAInternalInterface + RouteTableId: !Ref InternalRouteTable + PrivateSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnetA + PrivateSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnetB + ClusterPublicAddress: + Type: AWS::EC2::EIP + Properties: + Domain: vpc + MemberAPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + MemberBPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + ClusterAddressAssoc: + Type: AWS::EC2::EIPAssociation + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt ClusterPublicAddress.AllocationId + PrivateIpAddress: !Select [0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses] + MemberAAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt MemberAPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberBAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberBInstance + Properties: + NetworkInterfaceId: !Ref MemberBExternalInterface + AllocationId: !GetAtt MemberBPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress + MemberAInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberAExternalInterface, MemberAInternalInterface, ClusterPublicAddress, MemberBInternalInterface, MemberBExternalInterface, MemberAGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberAGatewayLaunchTemplate + Version: !GetAtt MemberAGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-A]] + - Key: x-chkp-member-ips + Value: !Join + - ':' + - - !Join [ '=', [ public-ip, !Ref MemberAPublicAddress ] ] + - !Join [ '=', [ external-private-ip, !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress ] ] + - !Join [ '=', [ internal-private-ip, !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress ] ] + - Key: x-chkp-cluster-ips + Value: !Join + - ':' + - - !Join [ '=', [ cluster-ip, !Ref ClusterPublicAddress ] ] + - !Join [ '=', [ secondary-external-private-ip, !Select [ 0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses ] ] ] + MemberBInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberBExternalInterface, MemberBInternalInterface, ClusterPublicAddress, MemberAInternalInterface, MemberBGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberBGatewayLaunchTemplate + Version: !GetAtt MemberBGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-B]] + - Key: x-chkp-member-ips + Value: !Join + - ':' + - - !Join [ '=', [ public-ip, !Ref MemberBPublicAddress ] ] + - !Join [ '=', [ external-private-ip, !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress ] ] + - !Join [ '=', [ internal-private-ip, !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress ] ] + - Key: x-chkp-cluster-ips + Value: !Join + - ':' + - - !Join [ '=', [ cluster-ip, !Ref ClusterPublicAddress ] ] + - !Join [ '=', [ secondary-external-private-ip, !Select [ 0, !GetAtt MemberBExternalInterface.SecondaryPrivateIpAddresses ] ] ] + MemberAGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberAExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberAInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenA=''${MemberAToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-a'] + - !Join ['', [' other_member_ip="', !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress, '"']] + - !Join ['', [' secondary_ip="', !Select [0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses], '"']] + - !Join ['', [' remote_secondary_ip="', !Select [0, !GetAtt MemberBExternalInterface.SecondaryPrivateIpAddresses], '"']] + - !Join ['', [' cluster_ip="', !Ref ClusterPublicAddress, '"']] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberAPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenA}\"" installationType=\"cross-az-cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"cross_az_cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" otherMemberIp=\"${other_member_ip}\" clusterIp=\"${cluster_ip}\" secondaryIp=\"${secondary_ip}\" otherMemberPrivateClusterIp=\"${remote_secondary_ip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + MemberBGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberBExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberBInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenB=''${MemberBToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-b'] + - !Join ['', [' other_member_ip="', !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress, '"']] + - !Join ['', [' secondary_ip="', !Select [0, !GetAtt MemberBExternalInterface.SecondaryPrivateIpAddresses], '"']] + - !Join ['', [' remote_secondary_ip="', !Select [0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses], '"']] + - !Join ['', [' cluster_ip="', !Ref ClusterPublicAddress, '"']] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberBPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join [ '', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"' ] ] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenB}\"" installationType=\"cross-az-cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"cross_az_cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" otherMemberIp=\"${other_member_ip}\" clusterIp=\"${cluster_ip}\" secondaryIp=\"${secondary_ip}\" otherMemberPrivateClusterIp=\"${remote_secondary_ip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version +Outputs: + ClusterPublicAddress: + Description: The public address of the cluster. + Value: !Ref ClusterPublicAddress + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !Ref MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberAPublicAddress]] + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !Join ['', ['https://', !Ref MemberAPublicAddress]] + MemberAExternalInterface: + Condition: AllocateAddress + Description: The external interface of member A. + Value: !Ref MemberAExternalInterface + MemberAPrivateExternalAddress: + Description: The primary external private address of member A. + Value: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberAPrivateAliasAddress: + Description: The secondary external private IP address of Member A. + Value: !Select [0, !GetAtt MemberAExternalInterface.SecondaryPrivateIpAddresses] + MemberAPrivateInternalAddress: + Description: The private Internal address of member A. + Value: !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !Ref MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberBPublicAddress]] + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !Join ['', ['https://', !Ref MemberBPublicAddress]] + MemberBPrivateExternalAddress: + Description: The primary external private address of member B. + Value: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress + MemberBPrivateAliasAddress: + Description: The secondary external private IP address of Member B. + Value: !Select [0, !GetAtt MemberBExternalInterface.SecondaryPrivateIpAddresses] + MemberBPrivateInternalAddress: + Description: The private Internal address of member B. + Value: !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] diff --git a/deprecated/aws/templates/R81/cluster/geo-cluster-master.yaml b/deprecated/aws/templates/R81/cluster/geo-cluster-master.yaml new file mode 100755 index 00000000..3c7c11a9 --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/geo-cluster-master.yaml @@ -0,0 +1,523 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Check Point cross AZ Cluster in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PrivateSubnet1CIDR + - PrivateSubnet2CIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + AvailabilityZones: + default: Availability Zones + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PrivateSubnet1CIDR: + default: Private subnet 1 CIDR + PrivateSubnet2CIDR: + default: Private subnet 2 CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved). + Type: List + MinLength: 2 + VPCCIDR: + Description: CIDR block for the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. The cluster's public IPs will be generated from this subnet. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. The cluster's public IPs will be generated from this subnet. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet1CIDR: + Description: CIDR block for private subnet 1 located in the 1st Availability Zone. The cluster's private IPs will be generated from this subnet. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet2CIDR: + Description: CIDR block for private subnet 2 located in the 2nd Availability Zone. The cluster's private IPs will be generated from this subnet. + Type: String + Default: 10.0.21.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the Security Gateways. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: When choosing "false", make sure the cluster members can connect to an ec2 endpoint. + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Description: The license to install on the Security Gateways. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to + get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between + Check Point components. Choose a random string consisting of at least 8 + alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: >- + Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: 2 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PrivateSubnet1CIDR: !Ref PrivateSubnet1CIDR + PrivateSubnet2CIDR: !Ref PrivateSubnet2CIDR + InternalRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPCStack + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: Private Subnets Route Table + ClusterStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/cluster/geo-cluster.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnetA: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PublicSubnetB: !GetAtt VPCStack.Outputs.PublicSubnet2ID + PrivateSubnetA: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + PrivateSubnetB: !GetAtt VPCStack.Outputs.PrivateSubnet2ID + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateExternalAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPrivateInternalAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateExternalAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPrivateInternalAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/cluster/geo-cluster.yaml b/deprecated/aws/templates/R81/cluster/geo-cluster.yaml new file mode 100755 index 00000000..bf9ec48a --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/geo-cluster.yaml @@ -0,0 +1,734 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point cross AZ Cluster into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnetA + - PublicSubnetB + - PrivateSubnetA + - PrivateSubnetB + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnetA: + default: Public subnet 1 + PublicSubnetB: + default: Public subnet 2 + PrivateSubnetA: + default: Private subnet 1 + PrivateSubnetB: + default: Private subnet 2 + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: you must select a VPC. + PublicSubnetA: + Description: Select a public subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the first Security Gateway. + PublicSubnetB: + Description: Select a public subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the second Security Gateway. + PrivateSubnetA: + Description: Select a private subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the first Security Gateway. + PrivateSubnetB: + Description: Select a private subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the second Security Gateway. + InternalRouteTable: + Description: Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the Route Table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the Security Gateways. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: When choosing "false", make sure the cluster members can connect to an ec2 endpoint. + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Description: The license to install on the Security Gateways. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to + get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between + Check Point components. Choose a random string consisting of at least 8 + alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: >- + Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + CreateRole: !Equals [!Ref GatewayPredefinedRole, ''] + ProvidedPassHash: !Not [!Equals [!Ref GatewayPasswordHash, '']] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + EmptyHostName: !Equals [!Ref GatewayHostname, ''] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ClusterReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ClusterReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: AllocateAddress + DependsOn: [MemberAInstance, MemberBInstance] + Properties: + Count: 2 + Handle: !Ref ClusterReadyHandle + Timeout: 1800 + ClusterRole: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cluster-iam-role.yaml + ClusterInstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [!If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole]] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName' ] + PolicyRole: !If [CreateRole, !GetAtt ClusterRole.Outputs.ClusterIAMRole, !Ref GatewayPredefinedRole] + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion, GW]] + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + MemberAExternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: External. + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnetA + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_ExternalInterface + MemberBExternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: External. + SourceDestCheck: false + GroupSet: [!Ref PermissiveSecurityGroup] + SubnetId: !Ref PublicSubnetB + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_ExternalInterface + MemberAInternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: Internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnetA + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_A_InternalInterface + MemberBInternalInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Description: Internal. + GroupSet: [!Ref PermissiveSecurityGroup] + SourceDestCheck: false + SubnetId: !Ref PrivateSubnetB + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - Member_B_InternalInterface + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + DependsOn: MemberAInternalInterface + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref MemberAInternalInterface + RouteTableId: !Ref InternalRouteTable + PrivateSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnetA + PrivateSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: ProvidedRouteTable + Properties: + RouteTableId: !Ref InternalRouteTable + SubnetId: !Ref PrivateSubnetB + MemberAInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberAInternalInterface, MemberAGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberAGatewayLaunchTemplate + Version: !GetAtt MemberAGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-A]] + MemberBInstance: + Type: AWS::EC2::Instance + DependsOn: [MemberBInternalInterface, MemberBGatewayLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MemberBGatewayLaunchTemplate + Version: !GetAtt MemberBGatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Join ['-', [!Ref GatewayName, Member-B]] + MemberAGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberAExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberAInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: !Base64 + 'Fn::Join': + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenA=''${MemberAToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-a'] + - !Join ['', [' other_member_ip="', !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress, '"']] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberAPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenA}\"" installationType=\"geo-cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"geo_cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" elasticIp=\"${eip}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" otherMemberIp=\"${other_member_ip}\" bootstrapScript64=\"${bootstrap}\"' + MemberBGatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref MemberBExternalInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref MemberBInternalInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !Ref ClusterInstanceProfile + UserData: !Base64 + 'Fn::Join': + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; tokenB=''${MemberBToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ClusterReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [EmptyHostName, ' hostname=""',!Sub ' hostname=${GatewayHostname}-member-b'] + - !Join ['', [' other_member_ip="', !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress, '"']] + - !Join ['', [' eip="', !If [AllocateAddress, !Ref MemberBPublicAddress, ''], '"']] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join [ '', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"' ] ] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${tokenB}\"" installationType=\"geo-cluster\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"geo_cluster\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" elasticIp=\"${eip}\" otherMemberIp=\"${other_member_ip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + MemberAPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + MemberBPublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + MemberAAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberAInstance + Properties: + NetworkInterfaceId: !Ref MemberAExternalInterface + AllocationId: !GetAtt MemberAPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberBAddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: MemberBInstance + Properties: + NetworkInterfaceId: !Ref MemberBExternalInterface + AllocationId: !GetAtt MemberBPublicAddress.AllocationId + PrivateIpAddress: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !Ref MemberAPublicAddress + MemberAPrivateExternalAddress: + Description: The private external address of member A. + Value: !GetAtt MemberAExternalInterface.PrimaryPrivateIpAddress + MemberAPrivateInternalAddress: + Description: The private internal address of member A. + Value: !GetAtt MemberAInternalInterface.PrimaryPrivateIpAddress + MemberAExternalInterface: + Description: The external interface of member A. + Value: !Ref MemberAExternalInterface + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberAPublicAddress]] + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !Join ['', ['https://', !Ref MemberAPublicAddress]] + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !Ref MemberBPublicAddress + MemberBPrivateExternalAddress: + Description: The private external address of member B. + Value: !GetAtt MemberBExternalInterface.PrimaryPrivateIpAddress + MemberBPrivateInternalAddress: + Description: The private internal address of member B. + Value: !GetAtt MemberBInternalInterface.PrimaryPrivateIpAddress + MemberBExternalInterface: + Description: The external interface of member B. + Value: !Ref MemberBExternalInterface + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref MemberBPublicAddress]] + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !Join ['', ['https://', !Ref MemberBPublicAddress]] +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/cluster/tgw-cross-az-cluster.yaml b/deprecated/aws/templates/R81/cluster/tgw-cross-az-cluster.yaml new file mode 100755 index 00000000..343d34b8 --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/tgw-cross-az-cluster.yaml @@ -0,0 +1,535 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point TGW Cross Availabilty Zone Cluster into an + existing VPC + (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnetA + - PublicSubnetB + - PrivateSubnetA + - PrivateSubnetB + - TgwHASubnetA + - TgwHASubnetB + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnetA: + default: Public subnet 1 + PublicSubnetB: + default: Public subnet 2 + PrivateSubnetA: + default: Private subnet 1 + PrivateSubnetB: + default: Private subnet 2 + TgwHASubnetA: + default: TGW HA subnet 1 + TgwHASubnetB: + default: TGW HA subnet 2 + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: you must select a VPC. + PublicSubnetA: + Description: Select a public subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the first Security Gateway. + PublicSubnetB: + Description: Select a public subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the second Security Gateway. + PrivateSubnetA: + Description: Select a private subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the first Security Gateway. + PrivateSubnetB: + Description: Select a private subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the second Security Gateway. + TgwHASubnetA: + Description: Select a TGW HA subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a TGW HA subnet for the first Security Gateway. + TgwHASubnetB: + Description: Select a TGW HA subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a TGW HAsubnet for the second Security Gateway. + InternalRouteTable: + Description: Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the Route Table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the Security Gateways. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Description: The license to install on the Security Gateways. + Type: String + Default: R81.20-BYOL + AllowedValues: + - R81.20-BYOL + - R81.20-PAYG-NGTP + - R81.20-PAYG-NGTX + - R82-BYOL + - R82-PAYG-NGTP + - R82-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + ClusterStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/cluster/cross-az-cluster.yaml + Parameters: + VPC: !Ref VPC + PublicSubnetA: !Ref PublicSubnetA + PublicSubnetB: !Ref PublicSubnetB + PrivateSubnetA: !Ref PrivateSubnetA + PrivateSubnetB: !Ref PrivateSubnetB + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary + TGWRouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: TGW Subnets + TGWDefaultRoute: + Type: AWS::EC2::Route + DependsOn: ClusterStack + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !GetAtt ClusterStack.Outputs.MemberAExternalInterface + RouteTableId: !Ref TGWRouteTable + TGWNSubnet1RouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: TGWRouteTable + Properties: + RouteTableId: !Ref TGWRouteTable + SubnetId: !Ref TgwHASubnetA + TGWSubnet2RouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: TGWRouteTable + Properties: + RouteTableId: !Ref TGWRouteTable + SubnetId: !Ref TgwHASubnetB +Outputs: + ClusterPublicAddress: + Description: The public address of the cluster. + Value: !GetAtt ClusterStack.Outputs.ClusterPublicAddress + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/cluster/tgw-ha-master.yaml b/deprecated/aws/templates/R81/cluster/tgw-ha-master.yaml new file mode 100755 index 00000000..a97886ba --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/tgw-ha-master.yaml @@ -0,0 +1,531 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a Check Point TGW HA cross AZ Cluster in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZones + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PrivateSubnet1CIDR + - PrivateSubnet2CIDR + - TgwSubnet1CIDR + - TgwSubnet2CIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + AvailabilityZones: + default: Availability Zones + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PrivateSubnet1CIDR: + default: Private subnet 1 CIDR + PrivateSubnet2CIDR: + default: Private subnet 2 CIDR + TgwSubnet1CIDR: + default: TGW HA subnet 1 CIDR + TgwSubnet2CIDR: + default: TGW HA subnet 2 CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + AvailabilityZones: + Description: The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved). + Type: List + MinLength: 2 + VPCCIDR: + Description: The CIDR block of the provided VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for public subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for public subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet1CIDR: + Description: CIDR block for private subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet2CIDR: + Description: CIDR block for private subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.21.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet1CIDR: + Description: CIDR block for TGW HA subnet 1 located in the 1st Availability Zone. + Type: String + Default: 10.0.12.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + TgwSubnet2CIDR: + Description: CIDR block for TGW HA subnet 2 located in the 2nd Availability Zone. + Type: String + Default: 10.0.22.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + AllocatePublicAddress: + Description: Allocate an Elastic IP for each cluster member, in addition to the shared cluster Elastic IP. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Default: false + Type: String + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Join [',', !Ref AvailabilityZones] + NumberOfAZs: 2 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnet1CIDR + PublicSubnet2CIDR: !Ref PublicSubnet2CIDR + PrivateSubnet1CIDR: !Ref PrivateSubnet1CIDR + PrivateSubnet2CIDR: !Ref PrivateSubnet2CIDR + CreateAttachmentSubnets: true + AttachmentSubnet1CIDR: !Ref TgwSubnet1CIDR + AttachmentSubnet2CIDR: !Ref TgwSubnet2CIDR + InternalRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPCStack + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: Private Subnets Route Table + ClusterStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/cluster/tgw-ha.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnetA: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PublicSubnetB: !GetAtt VPCStack.Outputs.PublicSubnet2ID + PrivateSubnetA: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + PrivateSubnetB: !GetAtt VPCStack.Outputs.PrivateSubnet2ID + TgwHASubnetA: !GetAtt VPCStack.Outputs.AttachmentSubnet1ID + TgwHASubnetB: !GetAtt VPCStack.Outputs.AttachmentSubnet2ID + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/cluster/tgw-ha.yaml b/deprecated/aws/templates/R81/cluster/tgw-ha.yaml new file mode 100755 index 00000000..beb37fc5 --- /dev/null +++ b/deprecated/aws/templates/R81/cluster/tgw-ha.yaml @@ -0,0 +1,527 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point TGW HA Cluster into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnetA + - PublicSubnetB + - PrivateSubnetA + - PrivateSubnetB + - TgwHASubnetA + - TgwHASubnetB + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - GatewayPredefinedRole + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - GatewaySICKey + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - MemberAToken + - MemberBToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + PublicSubnetA: + default: Public subnet 1 + PublicSubnetB: + default: Public subnet 2 + PrivateSubnetA: + default: Private subnet 1 + PrivateSubnetB: + default: Private subnet 2 + TgwHASubnetA: + default: TGW HA subnet 1 + TgwHASubnetB: + default: TGW HA subnet 2 + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Security Gateways instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate Elastic IPs for cluster members + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + GatewayPredefinedRole: + default: Existing IAM role name + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateways version & license + Shell: + default: Admin shell + GatewayPasswordHash: + default: Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + GatewaySICKey: + default: SIC key + MemberAToken: + default: Smart-1 Cloud Token for member A + MemberBToken: + default: Smart-1 Cloud Token for member B + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ConstraintDescription: you must select a VPC. + PublicSubnetA: + Description: Select a public subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the first Security Gateway. + PublicSubnetB: + Description: Select a public subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a public subnet for the second Security Gateway. + PrivateSubnetA: + Description: Select a private subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the first Security Gateway. + PrivateSubnetB: + Description: Select a private subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a private subnet for the second Security Gateway. + TgwHASubnetA: + Description: Select a TGW HA subnet for the first Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a TGW HA subnet for the first Security Gateway. + TgwHASubnetB: + Description: Select a TGW HA subnet for the second Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ConstraintDescription: you must select a TGW HAsubnet for the second Security Gateway. + InternalRouteTable: + Description: Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Cluster, this requires manual configuration in the Route Table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Cluster + GatewayInstanceType: + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the Security Gateways. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: When choosing "false", make sure the cluster members can connect to an ec2 endpoint. + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayPredefinedRole: + Description: A predefined IAM role to attach to the cluster profile. (optional) + Type: String + Default: '' + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Description: The license to install on the Security Gateways. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" to + get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '^[\$\./a-zA-Z0-9]*$' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections between + Check Point components. Choose a random string consisting of at least 8 + alphanumeric characters. + Type: String + AllowedPattern: '^[a-zA-Z0-9]{8,}$' + ConstraintDescription: At least 8 alpha numeric characters. + NoEcho: true + MemberAToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + MemberBToken: + Description: Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + ResourcesTagName: + Description: Name tag prefix of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The host name will be appended with member-a/b accordingly (optional). The name must not contain reserved words. For details, refer to sk40179. + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z]))?$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: >- + Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] +Resources: + ClusterStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/cluster/geo-cluster.yaml + Parameters: + VPC: !Ref VPC + PublicSubnetA: !Ref PublicSubnetA + PublicSubnetB: !Ref PublicSubnetB + PrivateSubnetA: !Ref PrivateSubnetA + PrivateSubnetB: !Ref PrivateSubnetB + InternalRouteTable: !Ref InternalRouteTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + GatewayPredefinedRole: !Ref GatewayPredefinedRole + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + GatewaySICKey: !Ref GatewaySICKey + MemberAToken: !Ref MemberAToken + MemberBToken: !Ref MemberBToken + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary + TGWRouteTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: TGW Subnets + TGWDefaultRoute: + Type: AWS::EC2::Route + DependsOn: ClusterStack + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !GetAtt ClusterStack.Outputs.MemberAExternalInterface + RouteTableId: !Ref TGWRouteTable + TGWNSubnet1RouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: TGWRouteTable + Properties: + RouteTableId: !Ref TGWRouteTable + SubnetId: !Ref TgwHASubnetA + TGWSubnet2RouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: TGWRouteTable + Properties: + RouteTableId: !Ref TGWRouteTable + SubnetId: !Ref TgwHASubnetB +Outputs: + MemberAPublicAddress: + Condition: AllocateAddress + Description: The public address of member A. + Value: !GetAtt ClusterStack.Outputs.MemberAPublicAddress + MemberASSH: + Condition: AllocateAddress + Description: SSH command to member A. + Value: !GetAtt ClusterStack.Outputs.MemberASSH + MemberAURL: + Condition: AllocateAddress + Description: URL to the member A portal. + Value: !GetAtt ClusterStack.Outputs.MemberAURL + MemberBPublicAddress: + Condition: AllocateAddress + Description: The public address of member B. + Value: !GetAtt ClusterStack.Outputs.MemberBPublicAddress + MemberBSSH: + Condition: AllocateAddress + Description: SSH command to member B. + Value: !GetAtt ClusterStack.Outputs.MemberBSSH + MemberBURL: + Condition: AllocateAddress + Description: URL to the member B portal. + Value: !GetAtt ClusterStack.Outputs.MemberBURL +Rules: + MemberATokenNotProvided: + RuleCondition: !Equals [!Ref MemberAToken, ''] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member A can not be empty" + Assert: !Equals [!Ref MemberBToken, ''] + MemberBTokenNotProvided: + RuleCondition: !Equals [ !Ref MemberBToken, '' ] + Assertions: + - AssertDescription: "Smart-1 Cloud Token for member B can not be empty" + Assert: !Equals [ !Ref MemberAToken, '' ] + MembersTokenValueEquals: + RuleCondition: !EachMemberEquals [ [ !Ref MemberBToken ], !Ref MemberAToken ] + Assertions: + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberAToken, '' ] + - AssertDescription: "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + Assert: !Equals [ !Ref MemberBToken, '' ] \ No newline at end of file diff --git a/deprecated/aws/templates/R81/gateway/gateway-master.yaml b/deprecated/aws/templates/R81/gateway/gateway-master.yaml new file mode 100755 index 00000000..83e507c2 --- /dev/null +++ b/deprecated/aws/templates/R81/gateway/gateway-master.yaml @@ -0,0 +1,495 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Security Gateway into a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZone + - VPCCIDR + - PublicSubnetCIDR + - PrivateSubnetCIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewaySICKey + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - GatewayToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + - Label: + default: Automatic Provisioning with Security Management Server Settings (optional) + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + AvailabilityZone: + default: Availability zone + VPCCIDR: + default: VPC CIDR + PublicSubnetCIDR: + default: Public subnet CIDR + PrivateSubnetCIDR: + default: Private subnet CIDR + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Gateway Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateway Version & license + Shell: + default: Admin shell + GatewaySICKey: + default: Gateway SIC key + GatewayToken: + default: Smart-1 Cloud Token + GatewayPasswordHash: + default: Gateway Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + ControlGatewayOverPrivateOrPublicAddress: + default: Gateway address + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + AvailabilityZone: + Description: The availability zone in which to deploy the instance. + Type: AWS::EC2::AvailabilityZone::Name + MinLength: 1 + VPCCIDR: + Description: The CIDR block of the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnetCIDR: + Description: The public subnet of the Security Gateway. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnetCIDR: + Description: The private subnet of the Security Gateway. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + GatewayName: + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The instance type of the Secutiry Gateways. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + NoEcho: true + GatewayToken: + Description: Follow the instructions in sk180501 to quickly connect this Gateway to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + Type: String + NoEcho: true + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the Security Gateway is provisioned using its private. + or public address + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic. + provisioning configuration. + Type: String + ConfigurationTemplate: + Description: A name of a Security Gateway configuration template in the automatic. + provisioning configuration. + Type: String + MaxLength: 30 +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Ref AvailabilityZone + NumberOfAZs: 1 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnetCIDR + CreatePrivateSubnets: true + PrivateSubnet1CIDR: !Ref PrivateSubnetCIDR + CreateAttachmentSubnets: false + InternalRoutingTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalRoutingTable + InternalNetworkRouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref InternalRoutingTable + SubnetId: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + GatewayStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gateway/gateway.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnet: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PrivateSubnet: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + InternalRouteTable: !Ref InternalRoutingTable + GatewayName: !Ref GatewayName + GatewayInstanceType: !Ref GatewayInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + GatewayVersion: !Ref GatewayVersion + Shell: !Ref Shell + GatewaySICKey: !Ref GatewaySICKey + GatewayToken: !Ref GatewayToken + GatewayPasswordHash: !Ref GatewayPasswordHash + GatewayMaintenancePasswordHash: !Ref GatewayMaintenancePasswordHash + ResourcesTagName: !Ref ResourcesTagName + GatewayHostname: !Ref GatewayHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + GatewayBootstrapScript: !Ref GatewayBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary + ControlGatewayOverPrivateOrPublicAddress: !Ref ControlGatewayOverPrivateOrPublicAddress + ManagementServer: !Ref ManagementServer + ConfigurationTemplate: !Ref ConfigurationTemplate +Outputs: + CheckPointInstancePublicAddress: + Condition: AllocateAddress + Description: The public address of the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.PublicAddress + CheckPointInstancePrivateExternalAddress: + Description: The private external address of the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.PrivateExternalAddress + CheckPointInstancePrivateInternalAddress: + Description: The private internal address of the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.PrivateInternalAddress + CheckPointInstanceSSH: + Condition: AllocateAddress + Description: SSH command to the Check Point instance. + Value: !GetAtt GatewayStack.Outputs.SSH + CheckPointInstanceURL: + Condition: AllocateAddress + Description: URL to the portal + Value: !GetAtt GatewayStack.Outputs.URL + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations + required to automatically provision the Gateways in the Auto Scaling Group, + such as what Security Policy to install and which Blades to enable, will be + placed under this template name. + Value: !Ref ConfigurationTemplate diff --git a/deprecated/aws/templates/R81/gateway/gateway.yaml b/deprecated/aws/templates/R81/gateway/gateway.yaml new file mode 100755 index 00000000..5f4e8f4a --- /dev/null +++ b/deprecated/aws/templates/R81/gateway/gateway.yaml @@ -0,0 +1,601 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Security Gateway into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnet + - PrivateSubnet + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - GatewayName + - GatewayInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - GatewayVersion + - Shell + - GatewaySICKey + - GatewayPasswordHash + - GatewayMaintenancePasswordHash + - Label: + default: Quick connect to Smart-1 Cloud (Recommended) + Parameters: + - GatewayToken + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - GatewayHostname + - AllowUploadDownload + - CloudWatch + - GatewayBootstrapScript + - NTPPrimary + - NTPSecondary + - Label: + default: Automatic Provisioning with Security Management Server Settings (optional) + Parameters: + - ControlGatewayOverPrivateOrPublicAddress + - ManagementServer + - ConfigurationTemplate + ParameterLabels: + VPC: + default: VPC + PublicSubnet: + default: Public subnet + PrivateSubnet: + default: Private subnet + InternalRouteTable: + default: Internal route table + GatewayName: + default: Gateway Name + GatewayInstanceType: + default: Gateway Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + GatewayVersion: + default: Gateway Version & license + Shell: + default: Admin shell + GatewaySICKey: + default: Gateway SIC key + GatewayToken: + default: Smart-1 Cloud Token + GatewayPasswordHash: + default: Gateway Password hash + GatewayMaintenancePasswordHash: + default: Gateway Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + GatewayHostname: + default: Gateway Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + GatewayBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + ControlGatewayOverPrivateOrPublicAddress: + default: Gateway address + ManagementServer: + default: Management Server + ConfigurationTemplate: + default: Configuration template +Parameters: + VPC: + Type: AWS::EC2::VPC::Id + MinLength: 1 + PublicSubnet: + Description: The public subnet of the security gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + PrivateSubnet: + Description: The private subnet of the security gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + InternalRouteTable: + Description: The route table id in which to set 0.0.0.0/0 route to the Gateway instance (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Gateway, this requires manual configuration in the route table. (optional) + Type: String + Default: '' + GatewayName: + Description: The name tag of the Security Gateway instances. (optional) + Type: String + Default: Check-Point-Gateway + GatewayInstanceType: + Description: The instance type of the Secutiry Gateway. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + Default: 100 + MinValue: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + GatewayVersion: + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG-NGTP + - R81-PAYG-NGTX + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + GatewaySICKey: + Description: The Secure Internal Communication key creates trusted connections + between Check Point components. Choose a random string consisting of at least + 8 alphanumeric characters. + Type: String + AllowedPattern: '[a-zA-Z0-9]{8,}' + NoEcho: true + GatewayToken: + Description: Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. + Type: String + AllowedPattern: '(^aHR0cHM6Ly9(.+)|(.*)\s[aHR0cHM6Ly9](.+)|^$)' + NoEcho: true + GatewayPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + GatewayMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + GatewayHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + GatewayBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + ControlGatewayOverPrivateOrPublicAddress: + Description: Determines if the Security Gateway is provisioned using its private + or public address. + Type: String + Default: private + AllowedValues: + - private + - public + ManagementServer: + Description: The name that represents the Security Management Server in the automatic + provisioning configuration. + Type: String + ConfigurationTemplate: + Description: A name of a Security Gateway configuration template in the automatic + provisioning configuration. + Type: String + MaxLength: 30 +Conditions: + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + ProvidedManagementParameters: !And [!Not [!Equals [!Ref ManagementServer, '']], !Not [!Equals [!Ref ConfigurationTemplate, '']]] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: AllocateAddress + DependsOn: GatewayInstance + Properties: + Handle: !Ref ReadyHandle + Timeout: 1800 + GatewayIAMRole: + Condition: EnableCloudWatch + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: [ ec2.amazonaws.com ] + Action: sts:AssumeRole + Path: / + GatewayInstanceProfile: + Condition: EnableCloudWatch + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [!Ref GatewayIAMRole] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName' ] + PolicyRole: !Ref GatewayIAMRole + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref GatewayVersion,GW]] + ExternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - ExternalNetworkInterface + Description: eth0 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PublicSubnet + InternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalNetworkInterface + Description: eth1 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PrivateSubnet + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + Tags: + - Key: Name + Value: + !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref InternalNetworkInterface + RouteTableId: !Ref InternalRouteTable + GatewayInstance: + Type: AWS::EC2::Instance + DependsOn: GatewayLaunchTemplate + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref GatewayLaunchTemplate + Version: !GetAtt GatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref GatewayName + - !If + - ProvidedManagementParameters + - Key: x-chkp-tags + Value: + !Join + - ':' + - - !Join ['=', [management, !Ref ManagementServer]] + - !Join ['=', [template,!Ref ConfigurationTemplate]] + - !Join ['=',[ip-address, !Ref ControlGatewayOverPrivateOrPublicAddress]] + - !Ref 'AWS::NoValue' + GatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref ExternalNetworkInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref InternalNetworkInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref GatewayInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [EnableCloudWatch, !Ref GatewayInstanceProfile, !Ref 'AWS::NoValue'] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; hostname=${GatewayHostname} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; eic=${EnableInstanceConnect} ; eip=${AllocatePublicAddress} ; token=''${GatewayToken}''' + - !If [AllocateAddress, !Sub ' wait_handle=''${ReadyHandle}''',!Ref 'AWS::NoValue'] + - !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref GatewaySICKey, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref GatewayMaintenancePasswordHash, ')"']] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref GatewayBootstrapScript, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref GatewayVersion]]}] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" "smart1CloudToken=\"${token}\"" installationType=\"gateway\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"gateway\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" allocatePublicAddress=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + PublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + AddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: AllocateAddress + DependsOn: GatewayInstance + Properties: + NetworkInterfaceId: !Ref ExternalNetworkInterface + AllocationId: !GetAtt PublicAddress.AllocationId + PrivateIpAddress: !GetAtt ExternalNetworkInterface.PrimaryPrivateIpAddress +Outputs: + PublicAddress: + Description: The public address of the Check Point instance. + Value: !Ref PublicAddress + Condition: AllocateAddress + PrivateExternalAddress: + Description: The private external address of the Check Point instance. + Value: !GetAtt ExternalNetworkInterface.PrimaryPrivateIpAddress + PrivateInternalAddress: + Description: The private internal address of the Check Point instance. + Value: !GetAtt InternalNetworkInterface.PrimaryPrivateIpAddress + SSH: + Description: SSH command to the Check Point instance. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref PublicAddress]] + Condition: AllocateAddress + URL: + Description: URL to the portal. + Value: !Join ['', ['https://', !Ref PublicAddress]] + Condition: AllocateAddress + ManagementName: + Description: The name that represents the Security Management Server. + Value: !Ref ManagementServer + ConfigurationTemplateName: + Description: The name that represents the configuration template. Configurations + required to automatically provision the Gateways in the Auto Scaling Group, + such as what Security Policy to install and which Blades to enable, will be + placed under this template name. + Value: !Ref ConfigurationTemplate diff --git a/deprecated/aws/templates/R81/gateway/standalone-master.yaml b/deprecated/aws/templates/R81/gateway/standalone-master.yaml new file mode 100755 index 00000000..ed1f12f6 --- /dev/null +++ b/deprecated/aws/templates/R81/gateway/standalone-master.yaml @@ -0,0 +1,443 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys either a manually configurable or a Check Point CloudGuard IaaS + Security Gateway & Management (Standalone) instance in a new VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - AvailabilityZone + - VPCCIDR + - PublicSubnetCIDR + - PrivateSubnetCIDR + - Label: + default: EC2 Instance Configuration + Parameters: + - StandaloneName + - StandaloneInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - StandaloneVersion + - Shell + - StandalonePasswordHash + - StandaloneMaintenancePasswordHash + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - StandaloneHostname + - AllowUploadDownload + - CloudWatch + - StandaloneBootstrapScript + - NTPPrimary + - NTPSecondary + - AdminCIDR + - GatewaysAddresses + ParameterLabels: + AvailabilityZone: + default: Availability zone + VPCCIDR: + default: VPC CIDR + PublicSubnetCIDR: + default: Public subnet CIDR + PrivateSubnetCIDR: + default: Private subnet CIDR + StandaloneName: + default: Standalone Name + StandaloneInstanceType: + default: Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + StandaloneVersion: + default: License + Shell: + default: Admin shell + StandalonePasswordHash: + default: Standalone Password hash + StandaloneMaintenancePasswordHash: + default: Gateway Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + StandaloneHostname: + default: Standalone Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + StandaloneBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses +Parameters: + AvailabilityZone: + Description: The availability zone in which to deploy the instance. + Type: AWS::EC2::AvailabilityZone::Name + MinLength: 1 + VPCCIDR: + Description: The CIDR block of the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnetCIDR: + Description: The public subnet of the Security Gateway. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnetCIDR: + Description: The private subnet of the Security Gateway. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + StandaloneName: + Type: String + Default: Check-Point-Instance + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Default: false + Type: String + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + StandaloneVersion: + Description: Standalone Version & License. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-PAYG-NGTP + - R81-BYOL + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + StandalonePasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + StandaloneMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + StandaloneInstanceType: + Description: The instance type of the Security Gateway & Management (Standalone) instance. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + StandaloneHostname: + Description: (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + StandaloneBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate. + with the Management Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Management. + Server. (optional) + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' +Conditions: + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] +Resources: + VPCStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/vpc.yaml + Parameters: + AvailabilityZones: !Ref AvailabilityZone + NumberOfAZs: 1 + VPCCIDR: !Ref VPCCIDR + PublicSubnet1CIDR: !Ref PublicSubnetCIDR + CreatePrivateSubnets: true + PrivateSubnet1CIDR: !Ref PrivateSubnetCIDR + CreateAttachmentSubnets: false + InternalRoutingTable: + Type: AWS::EC2::RouteTable + Properties: + VpcId: !GetAtt VPCStack.Outputs.VPCID + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalRoutingTable + InternalNetworkRouteAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Properties: + RouteTableId: !Ref InternalRoutingTable + SubnetId: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + StandaloneStack: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/gateway/standalone.yaml + Parameters: + VPC: !GetAtt VPCStack.Outputs.VPCID + PublicSubnet: !GetAtt VPCStack.Outputs.PublicSubnet1ID + PrivateSubnet: !GetAtt VPCStack.Outputs.PrivateSubnet1ID + InternalRouteTable: !Ref InternalRoutingTable + StandaloneName: !Ref StandaloneName + StandaloneInstanceType: !Ref StandaloneInstanceType + KeyName: !Ref KeyName + AllocatePublicAddress: !Ref AllocatePublicAddress + VolumeSize: !Ref VolumeSize + VolumeType: !Ref VolumeType + VolumeEncryption: !Ref VolumeEncryption + EnableInstanceConnect: !Ref EnableInstanceConnect + TerminationProtection: !Ref TerminationProtection + MetaDataToken: !Ref MetaDataToken + StandaloneVersion: !Ref StandaloneVersion + Shell: !Ref Shell + StandalonePasswordHash: !Ref StandalonePasswordHash + StandaloneMaintenancePasswordHash: !Ref StandaloneMaintenancePasswordHash + ResourcesTagName: !Ref ResourcesTagName + StandaloneHostname: !Ref StandaloneHostname + AllowUploadDownload: !Ref AllowUploadDownload + CloudWatch: !Ref CloudWatch + StandaloneBootstrapScript: !Ref StandaloneBootstrapScript + NTPPrimary: !Ref NTPPrimary + NTPSecondary: !Ref NTPSecondary + AdminCIDR: !Ref AdminCIDR + GatewaysAddresses: !Ref GatewaysAddresses +Outputs: + CheckPointInstancePublicAddress: + Condition: AllocateAddress + Description: The public address of the Check Point instance. + Value: !GetAtt StandaloneStack.Outputs.PublicAddress + CheckPointInstanceSSH: + Condition: AllocateAddress + Description: SSH command to the Check Point instance. + Value: !GetAtt StandaloneStack.Outputs.SSH + CheckPointInstanceURL: + Condition: AllocateAddress + Description: URL to the portal. + Value: !GetAtt StandaloneStack.Outputs.URL diff --git a/deprecated/aws/templates/R81/gateway/standalone.yaml b/deprecated/aws/templates/R81/gateway/standalone.yaml new file mode 100755 index 00000000..0bf218ef --- /dev/null +++ b/deprecated/aws/templates/R81/gateway/standalone.yaml @@ -0,0 +1,538 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys either a manually configurable or a Check Point CloudGuard IaaS + Security Gateway & Management (Standalone) instance into an existing VPC (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - PublicSubnet + - PrivateSubnet + - InternalRouteTable + - Label: + default: EC2 Instance Configuration + Parameters: + - StandaloneName + - StandaloneInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: Check Point Settings + Parameters: + - StandaloneVersion + - Shell + - StandalonePasswordHash + - StandaloneMaintenancePasswordHash + - Label: + default: Advanced Settings + Parameters: + - ResourcesTagName + - StandaloneHostname + - AllowUploadDownload + - CloudWatch + - StandaloneBootstrapScript + - NTPPrimary + - NTPSecondary + - AdminCIDR + - GatewaysAddresses + ParameterLabels: + VPC: + default: VPC + PublicSubnet: + default: Public subnet + PrivateSubnet: + default: Private subnet + InternalRouteTable: + default: Internal route table + StandaloneName: + default: Standalone Name + StandaloneInstanceType: + default: Standalone Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + StandaloneVersion: + default: License + Shell: + default: Admin shell + StandalonePasswordHash: + default: Standalone Password hash + StandaloneMaintenancePasswordHash: + default: Standalone Maintenance Password hash + ResourcesTagName: + default: Resources prefix tag + StandaloneHostname: + default: Standalone Hostname + AllowUploadDownload: + default: Allow upload & download + CloudWatch: + default: CloudWatch metrics + StandaloneBootstrapScript: + default: Bootstrap Script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses +Parameters: + VPC: + Type: AWS::EC2::VPC::Id + MinLength: 1 + PublicSubnet: + Description: The public subnet of the Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + PrivateSubnet: + Description: The private subnet of the Security Gateway. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + InternalRouteTable: + Description: The route table id in which to set 0.0.0.0/0 route to the Security Gateway instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Gateway, this requires manual configuration in the route table. (optional) + Type: String + Default: '' + StandaloneName: + Type: String + Default: Check-Point-Instance + StandaloneInstanceType: + Description: The instance type of the Security Gateway & Management (Standalone) instance. + Type: String + Default: c5.xlarge + AllowedValues: + - c4.large + - c4.xlarge + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: Must be a valid EC2 instance type + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Default: true + Type: String + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Ec2 Instance Connect is not supported with versions prior to R80.40. + Default: false + Type: String + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + StandaloneVersion: + Description: Standalone Version & License. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-PAYG-NGTP + - R81-BYOL + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + StandalonePasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + StandaloneMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ResourcesTagName: + Description: The name tag of the resources. (optional) + Type: String + Default: '' + StandaloneHostname: + Description: (optional) + Type: String + Default: '' + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + CloudWatch: + Description: Report Check Point specific CloudWatch metrics. + Type: String + Default: false + AllowedValues: + - true + - false + StandaloneBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '^[\.a-zA-Z0-9\-]*$' + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate. + with the Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Management. + Server. (optional) + Type: String + AllowedPattern: '^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2])))?$' +Conditions: + ProvidedResourcesTag: !Not [!Equals [!Ref ResourcesTagName, '']] + AllocateAddress: !Equals [!Ref AllocatePublicAddress, true] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + ProvidedRouteTable: !Not [!Equals [!Ref InternalRouteTable, '']] + EnableCloudWatch: !Equals [!Ref CloudWatch, true] + IsBYOL: !Equals [!Select [1, !Split ['-', !Ref StandaloneVersion]], 'BYOL'] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + ReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: AllocateAddress + Properties: {} + ReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: AllocateAddress + DependsOn: StandaloneInstance + Properties: + Handle: !Ref ReadyHandle + Timeout: 1800 + StandaloneIAMRole: + Condition: EnableCloudWatch + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: [ ec2.amazonaws.com ] + Action: sts:AssumeRole + Path: / + StandaloneInstanceProfile: + Condition: EnableCloudWatch + Type: AWS::IAM::InstanceProfile + Properties: + Path: / + Roles: [ !Ref StandaloneIAMRole ] + CloudwatchPolicy: + Condition: EnableCloudWatch + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/iam/cloudwatch-policy.yaml + Parameters: + PolicyName: !If [ ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName' ] + PolicyRole: !Ref StandaloneIAMRole + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !If [IsBYOL, !Join ['-', [!Ref StandaloneVersion,MGMT]], !Ref StandaloneVersion] + ExternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - ExternalNetworkInterface + Description: eth0 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PublicSubnet + InternalNetworkInterface: + Type: AWS::EC2::NetworkInterface + Properties: + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - InternalNetworkInterface + Description: eth1 + SourceDestCheck: false + GroupSet: + - !Ref PermissiveSecurityGroup + SubnetId: !Ref PrivateSubnet + PermissiveSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + Tags: + - Key: Name + Value: !Join + - _ + - - !If [ProvidedResourcesTag, !Ref ResourcesTagName, !Ref 'AWS::StackName'] + - PermissiveSecurityGroup + GroupDescription: Permissive security group. + VpcId: !Ref VPC + SecurityGroupIngress: + - IpProtocol: -1 + CidrIp: 0.0.0.0/0 + InternalDefaultRoute: + Type: AWS::EC2::Route + Condition: ProvidedRouteTable + Properties: + DestinationCidrBlock: 0.0.0.0/0 + NetworkInterfaceId: !Ref InternalNetworkInterface + RouteTableId: !Ref InternalRouteTable + StandaloneInstance: + Type: AWS::EC2::Instance + DependsOn: GatewayLaunchTemplate + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref GatewayLaunchTemplate + Version: !GetAtt GatewayLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref StandaloneName + GatewayLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + NetworkInterfaces: + - DeviceIndex: 0 + NetworkInterfaceId: !Ref ExternalNetworkInterface + - DeviceIndex: 1 + NetworkInterfaceId: !Ref InternalNetworkInterface + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref StandaloneInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [ EnableCloudWatch, !Ref StandaloneInstanceProfile, !Ref 'AWS::NoValue' ] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; hostname=${StandaloneHostname} ; allow_info=${AllowUploadDownload} ; cw=${CloudWatch} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; eic=${EnableInstanceConnect} ; eip=${AllocatePublicAddress} ; admin_subnet=${AdminCIDR}' + - !If [ AllocateAddress, !Sub ' wait_handle=''${ReadyHandle}''',!Ref 'AWS::NoValue' ] + - !Join [ '', [ ' bootstrap="$(echo ', 'Fn::Base64': !Ref StandaloneBootstrapScript, ')"' ] ] + - !Join [ '', [ ' pwd_hash="$(echo ', 'Fn::Base64': !Ref StandalonePasswordHash, ')"' ] ] + - !Join [ '', [ ' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref StandaloneMaintenancePasswordHash, ')"' ] ] + - !Sub [ ' version=${Version}', { Version: !Select [ 0, !Split [ '-', !Ref StandaloneVersion ] ] } ] + - ' python3 /etc/cloud_config.py enableCloudWatch=\"${cw}\" waitHandle=\"${wait_handle}\" installationType=\"standalone\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"standalone\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" adminSubnet=\"${admin_subnet}\" allocatePublicAddress=\"${eip}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + PublicAddress: + Type: AWS::EC2::EIP + Condition: AllocateAddress + Properties: + Domain: vpc + AddressAssoc: + Type: AWS::EC2::EIPAssociation + DependsOn: StandaloneInstance + Condition: AllocateAddress + Properties: + NetworkInterfaceId: !Ref ExternalNetworkInterface + AllocationId: !GetAtt PublicAddress.AllocationId + PrivateIpAddress: !GetAtt ExternalNetworkInterface.PrimaryPrivateIpAddress +Outputs: + PublicAddress: + Condition: AllocateAddress + Description: The public address of the Check Point instance. + Value: !Ref PublicAddress + SSH: + Condition: AllocateAddress + Description: SSH command to the Check Point instance. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref PublicAddress]] + URL: + Condition: AllocateAddress + Description: URL to the portal. + Value: !Join ['', ['https://', !Ref PublicAddress ]] diff --git a/deprecated/aws/templates/R81/iam/cloudwatch-policy.yaml b/deprecated/aws/templates/R81/iam/cloudwatch-policy.yaml new file mode 100755 index 00000000..a9a233e8 --- /dev/null +++ b/deprecated/aws/templates/R81/iam/cloudwatch-policy.yaml @@ -0,0 +1,39 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for selected permissions (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Policy Attributes + Parameters: + - PolicyName + - PolicyRole + ParameterLabels: + PolicyName: + default: Policy name + PolicyRole: + default: IAM role name +Parameters: + PolicyName: + Description: '' + Type: String + Default: 'Cloudwatch' + AllowedPattern: '[\w+=,.@-]+' + PolicyRole: + Description: '' + Type: String + AllowedPattern: '[\w+=,.@-]+' +Resources: + IAMPolicy: + Type: AWS::IAM::Policy + Properties: + PolicyName: !Sub "${PolicyName}-iam-policy" + PolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Action: + - cloudwatch:PutMetricData + Resource: '*' + Roles: + - !Ref PolicyRole diff --git a/deprecated/aws/templates/R81/iam/cluster-iam-role.yaml b/deprecated/aws/templates/R81/iam/cluster-iam-role.yaml new file mode 100755 index 00000000..85d52102 --- /dev/null +++ b/deprecated/aws/templates/R81/iam/cluster-iam-role.yaml @@ -0,0 +1,35 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for selected permissions (__VERSION__) +Resources: + ClusterIAMRole: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: [ec2.amazonaws.com] + Action: sts:AssumeRole + Path: / + Policies: + - PolicyName: ClusterPolicy + PolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Action: + - ec2:AssignPrivateIpAddresses + - ec2:AssociateAddress + - ec2:CreateRoute + - ec2:DescribeNetworkInterfaces + - ec2:DescribeRouteTables + - ec2:ReplaceRoute + Resource: '*' +Outputs: + ClusterIAMRole: + Description: The IAM role. + Value: !Ref ClusterIAMRole + ClusterARNRole: + Description: The IAM role ARN. + Value: !GetAtt ClusterIAMRole.Arn diff --git a/deprecated/aws/templates/R81/iam/cme-iam-role.yaml b/deprecated/aws/templates/R81/iam/cme-iam-role.yaml new file mode 100755 index 00000000..b9f6c2bf --- /dev/null +++ b/deprecated/aws/templates/R81/iam/cme-iam-role.yaml @@ -0,0 +1,159 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for selected permissions (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: IAM + Parameters: + - Permissions + - Label: + default: Advanced Configuration (optional) + Parameters: + - STSRoles + - TrustedAccount + ParameterLabels: + Permissions: + default: IAM role + STSRoles: + default: STS roles + TrustedAccount: + default: Trusted Account ID +Parameters: + Permissions: + Type: String + Default: Create with read permissions + AllowedValues: + - Create with read permissions + - Create with read-write permissions + - Create with assume role permissions (specify an STS role ARN) + STSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated list of ARNs, without spaces). + Type: String + Default: '' + TrustedAccount: + Description: A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it. + Type: String + Default: '' + AllowedPattern: '^([0-9]{12})|$' +Conditions: + AllowReadPermissions: !Or + - !Equals [!Ref Permissions, Create with read permissions] + - !Equals [!Ref Permissions, Create with read-write permissions] + AllowWritePermissions: !Equals [!Ref Permissions, Create with read-write permissions] + ProvidedSTSRoles: !Not [!Equals [!Ref STSRoles, '']] + NotProvidedTrustedAccount: !Equals ['', !Ref TrustedAccount] + ProvidedTrustedAccount: !Not [!Condition NotProvidedTrustedAccount] +Resources: + CMEIAMRole: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - ProvidedTrustedAccount + - Effect: Allow + Principal: + AWS: [!Ref TrustedAccount] + Action: ['sts:AssumeRole'] + - !Ref 'AWS::NoValue' + - !If + - NotProvidedTrustedAccount + - Effect: Allow + Principal: + Service: [ec2.amazonaws.com] + Action: ['sts:AssumeRole'] + - !Ref 'AWS::NoValue' + Path: / + Policies: + - PolicyName: CMEPolicy + PolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - ProvidedSTSRoles + - Effect: Allow + Action: ['sts:AssumeRole'] + Resource: !Split [',', !Ref STSRoles] + - !Ref 'AWS::NoValue' + - !If + - AllowReadPermissions + - Effect: Allow + Action: + - autoscaling:DescribeAutoScalingGroups + - ec2:DescribeRegions + - ec2:DescribeCustomerGateways + - ec2:DescribeInstances + - ec2:DescribeNetworkInterfaces + - ec2:DescribeRouteTables + - ec2:DescribeSecurityGroups + - ec2:DescribeSubnets + - ec2:DescribeTransitGateways + - ec2:DescribeTransitGatewayAttachments + - ec2:DescribeTransitGatewayRouteTables + - ec2:DescribeVpcs + - ec2:DescribeVpnGateways + - ec2:DescribeVpnConnections + - ec2:GetTransitGatewayAttachmentPropagations + - elasticloadbalancing:DescribeLoadBalancers + - elasticloadbalancing:DescribeTags + - elasticloadbalancing:DescribeListeners + - elasticloadbalancing:DescribeTargetGroups + - elasticloadbalancing:DescribeRules + - elasticloadbalancing:DescribeTargetHealth + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowWritePermissions + - Effect: Allow + Action: + - ec2:AssociateTransitGatewayRouteTable + - ec2:AttachVpnGateway + - ec2:CreateCustomerGateway + - ec2:CreateVpnConnection + - ec2:CreateVpnGateway + - ec2:DeleteCustomerGateway + - ec2:DeleteVpnConnection + - ec2:DeleteVpnGateway + - ec2:DetachVpnGateway + - ec2:DisableTransitGatewayRouteTablePropagation + - ec2:DisableVgwRoutePropagation + - ec2:DisassociateTransitGatewayRouteTable + - ec2:EnableTransitGatewayRouteTablePropagation + - ec2:EnableVgwRoutePropagation + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowWritePermissions + - Effect: Allow + Action: + - cloudformation:DescribeStacks + - cloudformation:DescribeStackResources + - cloudformation:ListStacks + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowWritePermissions + - Effect: Allow + Action: + - cloudformation:CreateStack + - cloudformation:DeleteStack + Resource: 'arn:aws:cloudformation:*:*:stack/vpn-by-tag--*/*' + - !Ref 'AWS::NoValue' + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Properties: + InstanceProfileName: !Ref CMEIAMRole + Roles: + - !Ref CMEIAMRole +Outputs: + CMEIAMRole: + Description: The IAM role. + Value: !Ref CMEIAMRole + CMEARNRole: + Description: The IAM role ARN. + Value: !GetAtt CMEIAMRole.Arn + InstanceProfile: + Description: The Instance Profile ARN. + Value: !GetAtt InstanceProfile.Arn \ No newline at end of file diff --git a/deprecated/aws/templates/R81/iam/sts-role.yaml b/deprecated/aws/templates/R81/iam/sts-role.yaml new file mode 100755 index 00000000..93f5cb40 --- /dev/null +++ b/deprecated/aws/templates/R81/iam/sts-role.yaml @@ -0,0 +1,119 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Creates an IAM role for cross account permissions (20190313) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Cross Account Permissions Configuration + Parameters: + - TrustedAccount + - Permissions + ParameterLabels: + TrustedAccount: + default: Trusted Account ID + STSPermissions: + default: IAM Role Permissions +Parameters: + TrustedAccount: + Description: A 12 digits number that represents the ID of the trusted account. + Type: String + AllowedPattern: '^[0-9]{12}$' + STSPermissions: + Description: Select Read-Write if you intend to use this role with Transit VPC. + Type: String + Default: Read only + AllowedValues: + - Read only + - Read-Write +Conditions: + AllowReadPermissions: !Or + - !Equals [!Ref STSPermissions, Read only] + - !Equals [!Ref STSPermissions, Read-Write] + AllowCreateVPNPermissions: !Equals [!Ref STSPermissions, Read-Write] +Resources: + Role: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + AWS: + - !Ref TrustedAccount + Action: + - sts:AssumeRole + Path: / + Policies: + - PolicyName: Policy + PolicyDocument: + Version: 2012-10-17 + Statement: + - !If + - AllowReadPermissions + - Effect: Allow + Action: + - ec2:DescribeInstances + - ec2:DescribeNetworkInterfaces + - ec2:DescribeSubnets + - ec2:DescribeVpcs + - ec2:DescribeVpnGateways + - ec2:DescribeVpnConnections + - ec2:DescribeSecurityGroups + - elasticloadbalancing:DescribeLoadBalancers + - elasticloadbalancing:DescribeTags + - elasticloadbalancing:DescribeListeners + - elasticloadbalancing:DescribeTargetGroups + - elasticloadbalancing:DescribeRules + - elasticloadbalancing:DescribeTargetHealth + - autoscaling:DescribeAutoScalingGroups + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowCreateVPNPermissions + - Effect: Allow + Action: + - ec2:DescribeCustomerGateways + - ec2:CreateCustomerGateway + - ec2:DeleteCustomerGateway + - ec2:DescribeRouteTables + - ec2:EnableVgwRoutePropagation + - ec2:DisableVgwRoutePropagation + - ec2:DescribeVpnGateways + - ec2:CreateVpnGateway + - ec2:AttachVpnGateway + - ec2:DetachVpnGateway + - ec2:DeleteVpnGateway + - ec2:DescribeVpnConnections + - ec2:CreateVpnConnection + - ec2:DeleteVpnConnection + - ec2:DescribeTransitGateways + - ec2:DescribeTransitGatewayRouteTables + - ec2:DescribeTransitGatewayAttachments + - ec2:AssociateTransitGatewayRouteTable + - ec2:DisassociateTransitGatewayRouteTable + - ec2:EnableTransitGatewayRouteTablePropagation + - ec2:DisableTransitGatewayRouteTablePropagation + - ec2:GetTransitGatewayAttachmentPropagations + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowCreateVPNPermissions + - Effect: Allow + Action: + - cloudformation:DescribeStacks + - cloudformation:DescribeStackResources + Resource: '*' + - !Ref 'AWS::NoValue' + - !If + - AllowCreateVPNPermissions + - Effect: Allow + Action: + - cloudformation:CreateStack + - cloudformation:DeleteStack + Resource: arn:aws:cloudformation:*:*:stack/vpn-by-tag--*/* + - !Ref 'AWS::NoValue' +Outputs: + Role: + Description: The role ARN to assume by the trusted account. + Value: !GetAtt Role.Arn diff --git a/deprecated/aws/templates/R81/management/management.yaml b/deprecated/aws/templates/R81/management/management.yaml new file mode 100755 index 00000000..e637fcfe --- /dev/null +++ b/deprecated/aws/templates/R81/management/management.yaml @@ -0,0 +1,585 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploys a Check Point Management Server (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - ManagementSubnet + - Label: + default: EC2 Instance Configuration + Parameters: + - ManagementName + - ManagementInstanceType + - KeyName + - AllocatePublicAddress + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: IAM Permissions (ignored when the installation is not Primary Management + Server) + Parameters: + - ManagementPermissions + - ManagementPredefinedRole + - ManagementSTSRoles + - Label: + default: Check Point Settings + Parameters: + - ManagementVersion + - Shell + - ManagementPasswordHash + - ManagementMaintenancePasswordHash + - Label: + default: Security Management Server Settings + Parameters: + - ManagementHostname + - ManagementInstallationType + - SICKey + - AllowUploadDownload + - AdminCIDR + - GatewayManagement + - GatewaysAddresses + - ManagementBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + ManagementSubnet: + default: Management subnet + ManagementName: + default: Management name + ManagementInstanceType: + default: Instance type + KeyName: + default: Key name + AllocatePublicAddress: + default: Allocate an Elastic IP + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + ManagementPermissions: + default: IAM role + ManagementPredefinedRole: + default: Existing IAM role name + ManagementSTSRoles: + default: STS roles + ManagementVersion: + default: Version & license + Shell: + default: Admin shell + ManagementPasswordHash: + default: Password hash + ManagementMaintenancePasswordHash: + default: Management Maintenance Password hash + ManagementHostname: + default: Management hostname + ManagementInstallationType: + default: Management installation type + SICKey: + default: SIC key + AllowUploadDownload: + default: Allow upload & download + AdminCIDR: + default: Administrator addresses + GatewayManagement: + default: Gateways management + GatewaysAddresses: + default: Gateways addresses + ManagementBootstrapScript: + default: Management bootstrap script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + ManagementSubnet: + Description: To access the instance from the internet, make sure the subnet has + a route to the internet. + Type: AWS::EC2::Subnet::Id + MinLength: 1 + ManagementName: + Description: The Management name tag. + Type: String + Default: Check-Point-Management + ManagementInstanceType: + Description: The instance type of the Security Management Server. + Type: String + Default: m5.xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + AllocatePublicAddress: + Description: Allocate an elastic IP for the Management. + Type: String + Default: true + AllowedValues: + - true + - false + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + ManagementPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + ManagementPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored. + if IAM role is not set to 'Use existing' + Type: String + Default: '' + ManagementSTSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated + list of ARNs, without spaces). Ignored if IAM role is set to 'None' or 'Use + existing'. + Type: CommaDelimitedList + Default: '' + ManagementVersion: + Description: The license to install on the Security Management Server. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + - R81-PAYG + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + ManagementPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + ManagementHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: mgmt-aws + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + ManagementInstallationType: + Description: Determines the Management Server installation type. + Type: String + Default: Primary management + AllowedValues: + - Primary management + - Secondary management + - Log Server + SICKey: + Description: >- + Mandatory only if deploying a secondary Management Server or Log Server, the Secure Internal + Communication key creates trusted connections between Check Point components. + Choose a random string consisting of at least 8 alphanumeric characters. + Type: String + Default: '' + AllowedPattern: '(|[a-zA-Z0-9]{8,})' + ConstraintDescription: Can be empty if this is a primary Management Server. Otherwise, + at least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate + with the Management Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Management + Server. + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + GatewayManagement: + Description: Select 'Over the internet' if any of the gateways you wish to manage + are not directly accessed via their private IP address. + Type: String + Default: Locally managed + AllowedValues: + - Locally managed + - Over the internet + ManagementBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '[\.a-zA-Z0-9\-]*' + NTPSecondary: + Description: (optional) + Type: String + Default: 0.pool.ntp.org + AllowedPattern: '[\.a-zA-Z0-9\-]*' +Conditions: + EIP: !Equals [!Ref AllocatePublicAddress, true] + ManageOverInternet: !Equals [!Ref GatewayManagement, Over the internet] + ManageOverInternetAndEIP: !And [!Condition EIP, !Condition ManageOverInternet] + CreateRole: !Or + - !Equals [!Ref ManagementPermissions, Create with assume role permissions (specify an STS role ARN)] + - !Equals [!Ref ManagementPermissions, Create with read permissions] + - !Equals [!Ref ManagementPermissions, Create with read-write permissions] + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + UseRole: !Not [!Equals [!Ref ManagementPermissions, None (configure later)]] + NoSIC: !Equals [!Ref SICKey, ''] + PreRole: !And [!Condition UseRole, !Not [!Condition CreateRole]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref ManagementVersion, MGMT]] + ManagementReadyHandle: + Type: AWS::CloudFormation::WaitConditionHandle + Condition: EIP + Properties: {} + ManagementReadyCondition: + Type: AWS::CloudFormation::WaitCondition + Condition: EIP + DependsOn: ManagementInstance + Properties: + Handle: !Ref ManagementReadyHandle + Timeout: 1800 + ManagementSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: Management security group + VpcId: !Ref VPC + SecurityGroupIngress: + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 257 + ToPort: 257 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 8211 + ToPort: 8211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18191 + ToPort: 18191 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18192 + ToPort: 18192 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18208 + ToPort: 18208 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18210 + ToPort: 18210 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18211 + ToPort: 18211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18221 + ToPort: 18221 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18264 + ToPort: 18264 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 22 + ToPort: 22 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 443 + ToPort: 443 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 18190 + ToPort: 18190 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 19009 + ToPort: 19009 + ManagementRoleStack: + Type: AWS::CloudFormation::Stack + Condition: CreateRole + Properties: + TemplateURL: __URL__/iam/cme-iam-role.yaml + Parameters: + Permissions: !Ref ManagementPermissions + STSRoles: !Join [',', !Ref ManagementSTSRoles] + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: PreRole + Properties: + Path: / + Roles: + - !Ref ManagementPredefinedRole + ManagementInstance: + Type: AWS::EC2::Instance + DependsOn: ManagementLaunchTemplate + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref ManagementLaunchTemplate + Version: !GetAtt ManagementLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref ManagementName + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: false + Description: eth0 + GroupSet: + - !Ref ManagementSecurityGroup + DeleteOnTermination: true + SubnetId: !Ref ManagementSubnet + ManagementLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref ManagementInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [ UseRole, !If [ PreRole, !Ref InstanceProfile, !GetAtt ManagementRoleStack.Outputs.CMEIAMRole ], !Ref 'AWS::NoValue' ] + UserData: + 'Fn::Base64': + !Join + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; hostname=${ManagementHostname} ; eic=${EnableInstanceConnect} ; admin_subnet=${AdminCIDR} ; eip=${AllocatePublicAddress} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; mgmt_install_type=''${ManagementInstallationType}''' + - !If [EIP, !Sub ' wait_handle=''${ManagementReadyHandle}''',!Ref 'AWS::NoValue'] + - !If [NoSIC, ' sic=""', !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref SICKey, ')"']]] + - !If [ManageOverInternetAndEIP, ' pub_mgmt=true', ' pub_mgmt=false'] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref ManagementBootstrapScript, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref ManagementPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref ManagementMaintenancePasswordHash, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref ManagementVersion]]}] + - ' python3 /etc/cloud_config.py waitHandle=\"${wait_handle}\" sicKey=\"${sic}\" installationType=\"management\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"management\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" "management_installation_type=\"${mgmt_install_type}\"" adminSubnet=\"${admin_subnet}\" allocatePublicAddress=\"${eip}\" overTheInternet=\"${pub_mgmt}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version + PublicAddress: + Type: AWS::EC2::EIP + Condition: EIP + Properties: + Domain: vpc + AddressAssoc: + Type: AWS::EC2::EIPAssociation + Condition: EIP + DependsOn: ManagementInstance + Properties: + InstanceId: !Ref ManagementInstance + AllocationId: !GetAtt PublicAddress.AllocationId +Outputs: + PublicAddress: + Condition: EIP + Description: The public address of the Management Server. + Value: !Ref PublicAddress + SSH: + Condition: EIP + Description: SSH command. + Value: !Join ['', ['ssh -i ', !Ref KeyName, ' admin@', !Ref PublicAddress]] + URL: + Condition: EIP + Description: URL to the portal. + Value: !Join ['', ['https://', !Ref PublicAddress]] diff --git a/deprecated/aws/templates/R81/management/mds.yaml b/deprecated/aws/templates/R81/management/mds.yaml new file mode 100755 index 00000000..4a8d3e51 --- /dev/null +++ b/deprecated/aws/templates/R81/management/mds.yaml @@ -0,0 +1,529 @@ +AWSTemplateFormatVersion: '2010-09-09' +Description: Deploys a Check Point Multi-Domain Server (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: VPC Network Configuration + Parameters: + - VPC + - MDSSubnet + - Label: + default: EC2 Instance Configuration + Parameters: + - MDSName + - MDSInstanceType + - KeyName + - VolumeSize + - VolumeType + - VolumeEncryption + - EnableInstanceConnect + - TerminationProtection + - MetaDataToken + - Label: + default: IAM Permissions (ignored when the installation type is not Primary + Multi-Domain Server) + Parameters: + - MDSPermissions + - MDSPredefinedRole + - MDSSTSRoles + - Label: + default: Check Point Settings + Parameters: + - MDSVersion + - Shell + - MDSPasswordHash + - MDSMaintenancePasswordHash + - Label: + default: Multi-Domain Server Settings + Parameters: + - MDSHostname + - MDSInstallationType + - MDSSICKey + - AllowUploadDownload + - AdminCIDR + - GatewaysAddresses + - MDSBootstrapScript + - NTPPrimary + - NTPSecondary + ParameterLabels: + VPC: + default: VPC + MDSSubnet: + default: MDS subnet + MDSName: + default: MDS name + MDSInstanceType: + default: Instance type + KeyName: + default: Key name + VolumeSize: + default: Root volume size (GB) + VolumeType: + default: Volume Type + VolumeEncryption: + default: Volume encryption KMS key identifier + EnableInstanceConnect: + default: Enable AWS Instance Connect + TerminationProtection: + default: Termination Protection + MetaDataToken: + default: Metadata HTTP token + MDSPermissions: + default: IAM role + MDSPredefinedRole: + default: Existing IAM role name + MDSSTSRoles: + default: STS roles + MDSVersion: + default: Version & license + Shell: + default: Admin shell + MDSPasswordHash: + default: Password hash + MDSMaintenancePasswordHash: + default: MDS Maintenance Password hash + MDSHostname: + default: MDS hostname + MDSInstallationType: + default: MDS installation type + MDSSICKey: + default: SIC key + AllowUploadDownload: + default: Allow upload & download + AdminCIDR: + default: Administrator addresses + GatewaysAddresses: + default: Gateways addresses + MDSBootstrapScript: + default: MDS Bootstrap script + NTPPrimary: + default: Primary NTP server + NTPSecondary: + default: Secondary NTP server +Parameters: + VPC: + Description: Select an existing VPC. + Type: AWS::EC2::VPC::Id + MinLength: 1 + MDSSubnet: + Description: To access the instance from the internet, make sure the subnet has. + a route to the internet + Type: AWS::EC2::Subnet::Id + MinLength: 1 + MDSName: + Description: The MDS name tag. + Type: String + Default: Check-Point-MDS + MDSInstanceType: + Description: The instance type of the Multi-Domain Server. + Type: String + Default: m5.2xlarge + AllowedValues: + - c5.large + - c5.xlarge + - c5.2xlarge + - c5.4xlarge + - c5.9xlarge + - c5.12xlarge + - c5.18xlarge + - c5.24xlarge + - c5n.large + - c5n.xlarge + - c5n.2xlarge + - c5n.4xlarge + - c5n.9xlarge + - c5n.18xlarge + - c5d.large + - c5d.xlarge + - c5d.2xlarge + - c5d.4xlarge + - c5d.9xlarge + - c5d.12xlarge + - c5d.18xlarge + - c5d.24xlarge + - m5.large + - m5.xlarge + - m5.2xlarge + - m5.4xlarge + - m5.8xlarge + - m5.12xlarge + - m5.16xlarge + - m5.24xlarge + - m6i.large + - m6i.xlarge + - m6i.2xlarge + - m6i.4xlarge + - m6i.8xlarge + - m6i.12xlarge + - m6i.16xlarge + - m6i.24xlarge + - m6i.32xlarge + - c6i.large + - c6i.xlarge + - c6i.2xlarge + - c6i.4xlarge + - c6i.8xlarge + - c6i.12xlarge + - c6i.16xlarge + - c6i.24xlarge + - c6i.32xlarge + - c6in.large + - c6in.xlarge + - c6in.2xlarge + - c6in.4xlarge + - c6in.8xlarge + - c6in.12xlarge + - c6in.16xlarge + - c6in.24xlarge + - c6in.32xlarge + - r5.large + - r5.xlarge + - r5.2xlarge + - r5.4xlarge + - r5.8xlarge + - r5.12xlarge + - r5.16xlarge + - r5.24xlarge + - r5a.large + - r5a.xlarge + - r5a.2xlarge + - r5a.4xlarge + - r5a.8xlarge + - r5a.12xlarge + - r5a.16xlarge + - r5a.24xlarge + - r5b.large + - r5b.xlarge + - r5b.2xlarge + - r5b.4xlarge + - r5b.8xlarge + - r5b.12xlarge + - r5b.16xlarge + - r5b.24xlarge + - r5n.large + - r5n.xlarge + - r5n.2xlarge + - r5n.4xlarge + - r5n.8xlarge + - r5n.12xlarge + - r5n.16xlarge + - r5n.24xlarge + - r6i.large + - r6i.xlarge + - r6i.2xlarge + - r6i.4xlarge + - r6i.8xlarge + - r6i.12xlarge + - r6i.16xlarge + - r6i.24xlarge + - r6i.32xlarge + - m6a.large + - m6a.xlarge + - m6a.2xlarge + - m6a.4xlarge + - m6a.8xlarge + - m6a.12xlarge + - m6a.16xlarge + - m6a.24xlarge + - m6a.32xlarge + - m6a.48xlarge + ConstraintDescription: must be a valid EC2 instance type. + KeyName: + Description: The EC2 Key Pair to allow SSH access to the instance. + Type: AWS::EC2::KeyPair::KeyName + MinLength: 1 + ConstraintDescription: must be the name of an existing EC2 KeyPair. + VolumeSize: + Type: Number + MinValue: 100 + Default: 100 + VolumeType: + Description: General Purpose SSD Volume Type + Type: String + Default: gp3 + AllowedValues: + - gp3 + - gp2 + VolumeEncryption: + Description: KMS or CMK key Identifier - Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs'). + Type: String + Default: alias/aws/ebs + EnableInstanceConnect: + Description: Enable SSH connection over AWS web console. + Type: String + Default: false + AllowedValues: + - true + - false + TerminationProtection: + Description: Prevents an instance from accidental termination. + Type: String + Default: false + AllowedValues: + - true + - false + MetaDataToken: + Description: Set true to deploy the instance with metadata v2 token required. + Type: String + Default: true + AllowedValues: + - true + - false + MDSPermissions: + Description: IAM role to attach to the instance profile. + Type: String + Default: Create with read permissions + AllowedValues: + - None (configure later) + - Use existing (specify an existing IAM role name) + - Create with assume role permissions (specify an STS role ARN) + - Create with read permissions + - Create with read-write permissions + MDSPredefinedRole: + Description: A predefined IAM role to attach to the instance profile. Ignored + if IAM role is not set to 'Use existing'. + Type: String + Default: '' + MDSSTSRoles: + Description: The IAM role will be able to assume these STS Roles (comma separated + list of ARNs, without spaces). Ignored if IAM role is set to 'None' or 'Use + existing'. + Type: CommaDelimitedList + Default: '' + MDSVersion: + Description: The license to install on the Multi-Domain Server. + Type: String + Default: R81-BYOL + AllowedValues: + - R81-BYOL + Shell: + Description: Change the admin shell to enable advanced command line configuration. + Type: String + Default: /etc/cli.sh + AllowedValues: + - /etc/cli.sh + - /bin/bash + - /bin/csh + - /bin/tcsh + MDSPasswordHash: + Description: Admin user's password hash (use command "openssl passwd -6 PASSWORD" + to get the PASSWORD's hash). (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + MDSMaintenancePasswordHash: + Description: Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes (use command " grub2-mkpasswd-pbkdf2" to get the PASSWORD's hash). For R81.10 and below the Admin user's password is used also as maintenance-mode password. (optional) + Type: String + Default: '' + AllowedPattern: '[\$\./a-zA-Z0-9]*' + NoEcho: true + MDSHostname: + Description: The name must not contain reserved words. For details, refer to sk40179. (optional) + Type: String + Default: mds-aws + AllowedPattern: '^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$' + ConstraintDescription: A valid hostname label or an empty string. + MDSInstallationType: + Description: Determines the Multi-Domain Server installation type. + Type: String + Default: Primary Multi-Domain Server + AllowedValues: + - Primary Multi-Domain Server + - Secondary Multi-Domain Server + - Multi-Domain Log Server + MDSSICKey: + Description: >- + Mandatory if deploying a Secondary Multi-Domain Server or Multi-Domain Log Server, + the Secure Internal Communication key creates trusted connections between Check + Point components. Choose a random string consisting of at least 8 alphanumeric + characters. + Type: String + Default: '' + AllowedPattern: '(|[a-zA-Z0-9]{8,})' + ConstraintDescription: Can be empty if this is a Primary Multi-Domain Server. + Otherwise, at least 8 alpha numeric characters. + NoEcho: true + AllowUploadDownload: + Description: Automatically download updates and share statistical data for product improvement purpose. + Type: String + Default: true + AllowedValues: + - true + - false + AdminCIDR: + Description: Allow web, SSH, and graphical clients only from this network to communicate + with the Multi-Domain Server. The address should be either 0.0.0.0/0 (any address) or /32 (specific address) + Type: String + AllowedPattern: '^((0.0.0.0\/0)|)$|^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/32)$' + ConstraintDescription: Administrator address must be either 0.0.0.0/0 or /32 + GatewaysAddresses: + Description: Allow gateways only from this network to communicate with the Multi-Domain. + Server + Type: String + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/([0-9]|[1-2][0-9]|3[0-2]))$' + MDSBootstrapScript: + Description: An optional script with semicolon (;) separated commands to run on the initial boot. (optional) + Type: String + Default: '' + NoEcho: true + NTPPrimary: + Description: (optional) + Type: String + Default: 169.254.169.123 + AllowedPattern: '[\.a-zA-Z0-9\-]*' + NTPSecondary: + Description: (optional) + Type: String + Default: '0.pool.ntp.org' + AllowedPattern: '[\.a-zA-Z0-9\-]*' +Conditions: + EncryptedVolume: !Not [!Equals [!Ref VolumeEncryption, '']] + CreateRole: !And + - !Or + - !Condition PrimaryMDS + - !Condition SecondaryMDS + - !Or + - !Equals [!Ref MDSPermissions, Create with assume role permissions (specify an STS role ARN)] + - !Equals [!Ref MDSPermissions, Create with read permissions] + - !Equals [!Ref MDSPermissions, Create with read-write permissions] + UseRole: !And [!Or [!Condition PrimaryMDS, !Condition SecondaryMDS], !Not [!Equals [!Ref MDSPermissions, None (configure later)]]] + PrimaryMDS: !Equals [!Ref MDSInstallationType, Primary Multi-Domain Server] + SecondaryMDS: !Equals [!Ref MDSInstallationType, Secondary Multi-Domain Server] + PreRole: !And [!Condition UseRole, !Not [!Condition CreateRole]] + EnableMetaDataToken: !Equals [!Ref MetaDataToken, true] +Resources: + AMI: + Type: AWS::CloudFormation::Stack + Properties: + TemplateURL: __URL__/utils/amis.yaml + Parameters: + Version: !Join ['-', [!Ref MDSVersion, MGMT]] + MDSSecurityGroup: + Type: AWS::EC2::SecurityGroup + Properties: + GroupDescription: MDS security group + VpcId: !Ref VPC + SecurityGroupIngress: + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 257 + ToPort: 257 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 8211 + ToPort: 8211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18191 + ToPort: 18191 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18192 + ToPort: 18192 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18208 + ToPort: 18208 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18210 + ToPort: 18210 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18211 + ToPort: 18211 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18221 + ToPort: 18221 + - CidrIp: !Ref GatewaysAddresses + IpProtocol: tcp + FromPort: 18264 + ToPort: 18264 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 22 + ToPort: 22 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 443 + ToPort: 443 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 18190 + ToPort: 18190 + - CidrIp: !Ref AdminCIDR + IpProtocol: tcp + FromPort: 19009 + ToPort: 19009 + MDSRoleStack: + Type: AWS::CloudFormation::Stack + Condition: CreateRole + Properties: + TemplateURL: __URL__/iam/cme-iam-role.yaml + Parameters: + Permissions: !Ref MDSPermissions + STSRoles: !Join [',', !Ref MDSSTSRoles] + InstanceProfile: + Type: AWS::IAM::InstanceProfile + Condition: PreRole + Properties: + Path: / + Roles: + - !Ref MDSPredefinedRole + MDSInstance: + Type: AWS::EC2::Instance + DependsOn: [MDSSecurityGroup, MDSLaunchTemplate] + Properties: + LaunchTemplate: + LaunchTemplateId: !Ref MDSLaunchTemplate + Version: !GetAtt MDSLaunchTemplate.LatestVersionNumber + DisableApiTermination: !Ref TerminationProtection + Tags: + - Key: Name + Value: !Ref MDSName + NetworkInterfaces: + - DeviceIndex: 0 + AssociatePublicIpAddress: false + Description: eth0 + GroupSet: + - !Ref MDSSecurityGroup + DeleteOnTermination: true + SubnetId: !Ref MDSSubnet + MDSLaunchTemplate: + Type: AWS::EC2::LaunchTemplate + Properties: + LaunchTemplateData: + KeyName: !Ref KeyName + ImageId: !GetAtt AMI.Outputs.ImageId + InstanceType: !Ref MDSInstanceType + MetadataOptions: + HttpTokens: !If [EnableMetaDataToken, required, optional] + BlockDeviceMappings: + - DeviceName: '/dev/xvda' + Ebs: + Encrypted: !If [ EncryptedVolume, true, false ] + KmsKeyId: !If [ EncryptedVolume, !Ref VolumeEncryption, !Ref 'AWS::NoValue' ] + VolumeType: !Ref VolumeType + VolumeSize: !Ref VolumeSize + IamInstanceProfile: + Name: !If [ UseRole, !If [ PreRole, !Ref InstanceProfile, !GetAtt MDSRoleStack.Outputs.CMEIAMRole ], !Ref 'AWS::NoValue' ] + UserData: !Base64 + Fn::Join: + - |+ + + - - '#cloud-config' + - 'runcmd:' + - ' - |' + - ' set -e' + - !Sub ' admin_shell=${Shell} ; allow_info=${AllowUploadDownload} ; hostname=${MDSHostname} ; eic=${EnableInstanceConnect} ; ntp1=${NTPPrimary} ; ntp2=${NTPSecondary} ; admin_subnet=${AdminCIDR}' + - !If [PrimaryMDS, ' primary=true ; secondary=false', !If [SecondaryMDS, ' primary=false ; secondary=true', ' primary=false ; secondary=false']] + - !If [PrimaryMDS, ' sic=notused', !Join ['', [' sic="$(echo ', 'Fn::Base64': !Ref MDSSICKey, ')"']]] + - !Join ['', [' bootstrap="$(echo ', 'Fn::Base64': !Ref MDSBootstrapScript, ')"']] + - !Join ['', [' pwd_hash="$(echo ', 'Fn::Base64': !Ref MDSPasswordHash, ')"']] + - !Join ['', [' maintenance_pwd_hash="$(echo ', 'Fn::Base64': !Ref MDSMaintenancePasswordHash, ')"']] + - !Sub [' version=${Version}', {Version: !Select [0, !Split ['-', !Ref MDSVersion]]}] + - ' python3 /etc/cloud_config.py sicKey=\"${sic}\" installationType=\"mds\" osVersion=\"${version}\" allowUploadDownload=\"${allow_info}\" templateVersion=\"__VERSION__\" templateName=\"mds\" shell=\"${admin_shell}\" enableInstanceConnect=\"${eic}\" hostName=\"${hostname}\" ntpPrimary=\"${ntp1}\" ntpSecondary=\"${ntp2}\" passwordHash=\"${pwd_hash}\" MaintenanceModePassword=\"${maintenance_pwd_hash}\" primary=\"${primary}\" secondary=\"${secondary}\" adminSubnet=\"${admin_subnet}\" bootstrapScript64=\"${bootstrap}\"' + VersionDescription: Initial template version \ No newline at end of file diff --git a/deprecated/aws/templates/R81/utils/copy-lambda-zip.yaml b/deprecated/aws/templates/R81/utils/copy-lambda-zip.yaml new file mode 100755 index 00000000..f5cdcfd2 --- /dev/null +++ b/deprecated/aws/templates/R81/utils/copy-lambda-zip.yaml @@ -0,0 +1,138 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Create an S3 bucket in the same region as the stack, and copy a zip of a Lambda from remote bucket to it (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Lambda zip location + Parameters: + - SourceBucketName + - FolderName + - LambdaPathObjects + ParameterLabels: + SourceBucketName: + default: Source Bucket Name + FolderName: + default: Folder Name + LambdaPathObjects: + default: Lambda Path +Parameters: + SourceBucketName: + Description: The source bucket (e.g. lambda-bucket ). + Type: String + MinLength: 1 + FolderName: + Description: The source folder (e.g. lambda-prefix/ ). + Type: String + AllowedPattern: '^[0-9a-zA-Z-_/]*/$' + LambdaPathObjects: + Description: A zip file (e.g. lambda.zip). + Type: String + AllowedPattern: '.*\.zip' +Resources: + LambdaZipBucket: + Type: AWS::S3::Bucket + CopyZips: + Type: Custom::CopyZips + Properties: + ServiceToken: !GetAtt CopyZipsFunction.Arn + SourceBucket: !Ref SourceBucketName + DestBucket: !Ref LambdaZipBucket + Prefix: !Ref FolderName + Objects: + - !Ref LambdaPathObjects + CopyZipsRole: + Type: AWS::IAM::Role + Properties: + AssumeRolePolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Principal: + Service: lambda.amazonaws.com + Action: sts:AssumeRole + Path: / + Policies: + - PolicyName: !Sub lambda-copier-${LambdaZipBucket} + PolicyDocument: + Version: 2012-10-17 + Statement: + - Effect: Allow + Action: + - s3:GetObject + Resource: + - !Sub arn:aws:s3:::${SourceBucketName}/${FolderName}* + - Effect: Allow + Action: + - s3:PutObject + - s3:DeleteObject + Resource: + - !Sub arn:aws:s3:::${LambdaZipBucket}/${FolderName}* + CopyZipsFunction: + Type: AWS::Lambda::Function + Properties: + Description: Copies objects from a source S3 bucket to a destination. + Handler: index.handler + Runtime: python3.7 + Role: !GetAtt CopyZipsRole.Arn + Timeout: 240 + Code: + ZipFile: | + import json + import logging + import threading + import boto3 + import cfnresponse + + + def copy_objects(source_bucket, dest_bucket, prefix, objects): + s3 = boto3.client('s3') + for o in objects: + key = prefix + o + copy_source = {'Bucket': source_bucket, 'Key': key } + print(f'copy_source: {copy_source}') + print(f'dest_bucket = {dest_bucket}') + print(f'key = {key}') + s3.copy_object(CopySource=copy_source, Bucket=dest_bucket, Key=key) + + + def delete_objects(bucket, prefix, objects): + s3 = boto3.client('s3') + objects = {'Objects': [{'Key': prefix + o} for o in objects]} + s3.delete_objects(Bucket=bucket, Delete=objects) + + + def timeout(event, context): + logging.error('Execution is about to time out, sending failure' + ' response to CloudFormation') + cfnresponse.send(event, context, cfnresponse.FAILED, {}, None) + + + def handler(event, context): + # make sure we send a failure to CloudFormation if the function + # is going to timeout + timer = threading.Timer((context.get_remaining_time_in_millis() + / 1000.00) - 0.5, timeout, args=[event, context]) + timer.start() + + print(f'Received event: {json.dumps(event)}') + status = cfnresponse.SUCCESS + try: + source_bucket = event['ResourceProperties']['SourceBucket'] + dest_bucket = event['ResourceProperties']['DestBucket'] + prefix = event['ResourceProperties']['Prefix'] + objects = event['ResourceProperties']['Objects'] + if event['RequestType'] == 'Delete': + delete_objects(dest_bucket, prefix, objects) + else: + copy_objects(source_bucket, dest_bucket, prefix, objects) + except Exception as e: + logging.error('Exception: %s' % e, exc_info=True) + status = cfnresponse.FAILED + finally: + timer.cancel() + cfnresponse.send(event, context, status, {}, None) +Outputs: + LambdaZipBucket: + Description: The new S3 bucket in the local region. + Value: !Ref LambdaZipBucket \ No newline at end of file diff --git a/deprecated/aws/templates/R81/utils/tap-target-and-filter.yaml b/deprecated/aws/templates/R81/utils/tap-target-and-filter.yaml new file mode 100755 index 00000000..89c60ac5 --- /dev/null +++ b/deprecated/aws/templates/R81/utils/tap-target-and-filter.yaml @@ -0,0 +1,68 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: Deploy a traffic-mirror-filter and traffic-mirror-target (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: General Settings + Parameters: + - MirroringNetworkInterfaceId + - EnvironmentPrefix + ParameterLabels: + MirroringNetworkInterfaceId: + default: Mirroring target network interface id + EnvironmentPrefix: + default: Environment prefix for created resources +Parameters: + MirroringNetworkInterfaceId: + Description: The network interface ID to which all the traffic will be mirrored. + Type: String + AllowedPattern: '^eni-[a-z0-9]+$' + EnvironmentPrefix: + Description: The environment prefix for created resources. (optional) + Type: String + AllowedPattern: '[a-zA-Z0-9-_]*' + Default: cp-tap +Resources: + TrafficMirrorFilter: + Type: AWS::EC2::TrafficMirrorFilter + Properties: + Description: Traffic mirror filter. + Tags: + - Key: Name + Value: !Join ['-', [!Ref EnvironmentPrefix, traffic-filter]] + TrafficMirrorFilterRuleIngress: + Type: AWS::EC2::TrafficMirrorFilterRule + Properties: + Description: Traffic mirror filter rule - ingress. + DestinationCidrBlock: 0.0.0.0/0 + RuleAction: accept + RuleNumber: 100 + SourceCidrBlock: 0.0.0.0/0 + TrafficDirection: ingress + TrafficMirrorFilterId: !Ref TrafficMirrorFilter + TrafficMirrorFilterRuleEgress: + Type: AWS::EC2::TrafficMirrorFilterRule + Properties: + Description: Traffic mirror filter rule - egress. + DestinationCidrBlock: 0.0.0.0/0 + RuleAction: accept + RuleNumber: 100 + SourceCidrBlock: 0.0.0.0/0 + TrafficDirection: egress + TrafficMirrorFilterId: !Ref TrafficMirrorFilter + TrafficMirrorTarget: + Type: AWS::EC2::TrafficMirrorTarget + Properties: + Description: Traffic mirror target. + NetworkInterfaceId: !Ref MirroringNetworkInterfaceId + Tags: + - Key: Name + Value: !Join ['-', [!Ref EnvironmentPrefix, traffic-target]] +Outputs: + TrafficMirrorTargetId: + Description: Traffic mirror target id. + Value: !Ref TrafficMirrorTarget + TrafficMirrorFilterId: + Description: Traffic mirror filter id. + Value: !Ref TrafficMirrorFilter \ No newline at end of file diff --git a/deprecated/aws/templates/R81/utils/vpc.yaml b/deprecated/aws/templates/R81/utils/vpc.yaml new file mode 100755 index 00000000..e04e0832 --- /dev/null +++ b/deprecated/aws/templates/R81/utils/vpc.yaml @@ -0,0 +1,571 @@ +AWSTemplateFormatVersion: 2010-09-09 +Description: This template creates a Multi-AZ, multi-subnet VPC infrastructure (__VERSION__) +Metadata: + AWS::CloudFormation::Interface: + ParameterGroups: + - Label: + default: Availability Zone Configuration + Parameters: + - AvailabilityZones + - NumberOfAZs + - Label: + default: Network Configuration + Parameters: + - VPCCIDR + - PublicSubnet1CIDR + - PublicSubnet2CIDR + - PublicSubnet3CIDR + - PublicSubnet4CIDR + - CreatePrivateSubnets + - PrivateSubnet1CIDR + - PrivateSubnet2CIDR + - PrivateSubnet3CIDR + - PrivateSubnet4CIDR + - CreateAttachmentSubnets + - AttachmentSubnet1CIDR + - AttachmentSubnet2CIDR + - AttachmentSubnet3CIDR + - AttachmentSubnet4CIDR + ParameterLabels: + AvailabilityZones: + default: Availability Zones + NumberOfAZs: + default: Number of Availability Zones + VPCCIDR: + default: VPC CIDR + PublicSubnet1CIDR: + default: Public subnet 1 CIDR + PublicSubnet2CIDR: + default: Public subnet 2 CIDR + PublicSubnet3CIDR: + default: Public subnet 3 CIDR + PublicSubnet4CIDR: + default: Public subnet 4 CIDR + CreatePrivateSubnets: + default: Create private subnets + PrivateSubnet1CIDR: + default: Private subnet 1 CIDR + PrivateSubnet2CIDR: + default: Private subnet 2 CIDR + PrivateSubnet3CIDR: + default: Private subnet 3 CIDR + PrivateSubnet4CIDR: + default: Private subnet 4 CIDR + CreateAttachmentSubnets: + default: Create Attachment subnets + AttachmentSubnet1CIDR: + default: Attachment subnet 1 CIDR + AttachmentSubnet2CIDR: + default: Attachment subnet 2 CIDR + AttachmentSubnet3CIDR: + default: Attachment subnet 3 CIDR + AttachmentSubnet4CIDR: + default: Attachment subnet 4 CIDR +Parameters: + AvailabilityZones: + Description: 'List of Availability Zones to use for the subnets in the VPC. Note: The logical order is preserved.' + Type: List + MinLength: 1 + NumberOfAZs: + Description: Number of Availability Zones to use in the VPC. This must match your + selections in the list of Availability Zones parameter. + Type: Number + Default: 2 + MinValue: 1 + MaxValue: 4 + VPCCIDR: + Description: CIDR block for the VPC. + Type: String + Default: 10.0.0.0/16 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet1CIDR: + Description: CIDR block for the public DMZ subnet 1 located in Availability Zone 1. + Type: String + Default: 10.0.10.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet2CIDR: + Description: CIDR block for the public DMZ subnet 2 located in Availability Zone 2. + Type: String + Default: 10.0.20.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet3CIDR: + Description: CIDR block for the public DMZ subnet 3 located in Availability Zone 3. + Type: String + Default: 10.0.30.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PublicSubnet4CIDR: + Description: CIDR block for the public DMZ subnet 4 located in Availability Zone 4. + Type: String + Default: 10.0.40.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + CreatePrivateSubnets: + Description: Set to false to create only public subnets. If false, the CIDR parameters. + for ALL private subnets will be ignored. + Type: String + Default: true + AllowedValues: + - true + - false + PrivateSubnet1CIDR: + Description: CIDR block for private subnet 1 located in Availability Zone 1. + Type: String + Default: 10.0.11.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet2CIDR: + Description: CIDR block for private subnet 2 located in Availability Zone 2. + Type: String + Default: 10.0.21.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet3CIDR: + Description: CIDR block for private subnet 3 located in Availability Zone 3. + Type: String + Default: 10.0.31.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + PrivateSubnet4CIDR: + Description: CIDR block for private subnet 4 located in Availability Zone 4. + Type: String + Default: 10.0.41.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + CreateAttachmentSubnets: + Description: Set true for creating designated subnets for VPC attachments. If false, + the CIDR parameters for the Attachment subnets will be ignored. + Type: String + Default: false + AllowedValues: + - true + - false + AttachmentSubnet1CIDR: + Description: CIDR block for Attachment subnet 1 located in Availability Zone 1. + Type: String + Default: 10.0.12.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + AttachmentSubnet2CIDR: + Description: CIDR block for Attachment subnet 2 located in Availability Zone 2. + Type: String + Default: 10.0.22.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + AttachmentSubnet3CIDR: + Description: CIDR block for Attachment subnet 3 located in Availability Zone 3. + Type: String + Default: 10.0.32.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. + AttachmentSubnet4CIDR: + Description: CIDR block for Attachment subnet 4 located in Availability Zone 4. + Type: String + Default: 10.0.42.0/24 + AllowedPattern: '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\/(1[6-9]|2[0-8]))$' + ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/16-28. +Conditions: + 4AZs: !Equals [!Ref NumberOfAZs, 4] + 3AZs: !Or [!Equals [!Ref NumberOfAZs, 3], !Condition 4AZs] + 2AZs: !Or [!Equals [!Ref NumberOfAZs, 2], !Condition 3AZs] + PrivateSubnets: !Equals [!Ref CreatePrivateSubnets, true] + 2AZsPrivateSubnets: !And [!Condition PrivateSubnets, !Condition 2AZs] + 3AZsPrivateSubnets: !And [!Condition PrivateSubnets, !Condition 3AZs] + 4AZsPrivateSubnets: !And [!Condition PrivateSubnets, !Condition 4AZs] + AttachmentSubnets: !Equals [!Ref CreateAttachmentSubnets, true] + 2AZsAttachmentSubnets: !And [!Condition AttachmentSubnets, !Condition 2AZs] + 3AZsAttachmentSubnets: !And [!Condition AttachmentSubnets, !Condition 3AZs] + 4AZsAttachmentSubnets: !And [!Condition AttachmentSubnets, !Condition 4AZs] +Resources: + VPC: + Type: AWS::EC2::VPC + Properties: + CidrBlock: !Ref VPCCIDR + EnableDnsSupport: true + EnableDnsHostnames: true + Tags: + - Key: Name + Value: !Ref 'AWS::StackName' + InternetGateway: + Type: AWS::EC2::InternetGateway + Properties: + Tags: + - Key: Name + Value: !Ref 'AWS::StackName' + - Key: Network + Value: Public + VPCGatewayAttachment: + Type: AWS::EC2::VPCGatewayAttachment + DependsOn: [VPC, InternetGateway] + Properties: + VpcId: !Ref VPC + InternetGatewayId: !Ref InternetGateway + PublicSubnet1: + Type: AWS::EC2::Subnet + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 1 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnet2: + Condition: 2AZs + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 2 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnet3: + Condition: 3AZs + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 3 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnet4: + Condition: 4AZs + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PublicSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Public subnet 4 + - Key: Network + Value: Public + MapPublicIpOnLaunch: true + PublicSubnetRouteTable: + Type: AWS::EC2::RouteTable + DependsOn: VPC + Properties: + VpcId: !Ref VPC + Tags: + - Key: Name + Value: Public Subnets Route Table + - Key: Network + Value: Public + PublicSubnetRoute: + DependsOn: [VPCGatewayAttachment, PublicSubnetRouteTable] + Type: AWS::EC2::Route + Properties: + RouteTableId: !Ref PublicSubnetRouteTable + DestinationCidrBlock: 0.0.0.0/0 + GatewayId: !Ref InternetGateway + PublicSubnet1RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + DependsOn: [PublicSubnet1, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet1 + RouteTableId: !Ref PublicSubnetRouteTable + PublicSubnet2RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 2AZs + DependsOn: [PublicSubnet2, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet2 + RouteTableId: !Ref PublicSubnetRouteTable + PublicSubnet3RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 3AZs + DependsOn: [PublicSubnet3, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet3 + RouteTableId: !Ref PublicSubnetRouteTable + PublicSubnet4RouteTableAssociation: + Type: AWS::EC2::SubnetRouteTableAssociation + Condition: 4AZs + DependsOn: [PublicSubnet4, PublicSubnetRouteTable] + Properties: + SubnetId: !Ref PublicSubnet4 + RouteTableId: !Ref PublicSubnetRouteTable + PrivateSubnet1: + Type: AWS::EC2::Subnet + Condition: PrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 1 + - Key: Network + Value: Private + PrivateSubnet2: + Type: AWS::EC2::Subnet + Condition: 2AZsPrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 2 + - Key: Network + Value: Private + PrivateSubnet3: + Type: AWS::EC2::Subnet + Condition: 3AZsPrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 3 + - Key: Network + Value: Private + PrivateSubnet4: + Type: AWS::EC2::Subnet + Condition: 4AZsPrivateSubnets + DependsOn: VPC + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref PrivateSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Private subnet 4 + - Key: Network + Value: Private + AttachmentSubnet1: + Condition: AttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet1CIDR + AvailabilityZone: !Select [0, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 1 + - Key: Network + Value: Private + AttachmentSubnet2: + Condition: AttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet2CIDR + AvailabilityZone: !Select [1, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 2 + - Key: Network + Value: Private + AttachmentSubnet3: + Condition: 3AZsAttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet3CIDR + AvailabilityZone: !Select [2, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 3 + - Key: Network + Value: Private + AttachmentSubnet4: + Condition: 4AZsAttachmentSubnets + DependsOn: VPC + Type: AWS::EC2::Subnet + Properties: + VpcId: !Ref VPC + CidrBlock: !Ref AttachmentSubnet4CIDR + AvailabilityZone: !Select [3, !Ref AvailabilityZones] + Tags: + - Key: Name + Value: Attachment subnet 4 + - Key: Network + Value: Private +Outputs: + VPCID: + Value: !Ref VPC + Description: VPC ID. + Export: + Name: !Sub '${AWS::StackName}-VPCID' + VPCCIDR: + Value: !Ref VPCCIDR + Description: VPC CIDR + Export: + Name: !Sub '${AWS::StackName}-VPCCIDR' + PublicSubnet1CIDR: + Description: Public subnet 1 CIDR in Availability Zone 1. + Value: !Ref PublicSubnet1CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet1CIDR' + PublicSubnet1ID: + Description: Public subnet 1 ID in Availability Zone 1. + Value: !Ref PublicSubnet1 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet1ID' + PublicSubnet2CIDR: + Condition: 2AZs + Description: Public subnet 2 CIDR in Availability Zone 2. + Value: !Ref PublicSubnet2CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet2CIDR' + PublicSubnet2ID: + Condition: 2AZs + Description: Public subnet 2 ID in Availability Zone 2. + Value: !Ref PublicSubnet2 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet2ID' + PublicSubnet3CIDR: + Condition: 3AZs + Description: Public subnet 3 CIDR in Availability Zone 3. + Value: !Ref PublicSubnet3CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet3CIDR' + PublicSubnet3ID: + Condition: 3AZs + Description: Public subnet 3 ID in Availability Zone 3. + Value: !Ref PublicSubnet3 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet3ID' + PublicSubnet4CIDR: + Condition: 4AZs + Description: Public subnet 4 CIDR in Availability Zone 4. + Value: !Ref PublicSubnet4CIDR + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet4CIDR' + PublicSubnet4ID: + Condition: 4AZs + Description: Public subnet 4 ID in Availability Zone 4. + Value: !Ref PublicSubnet4 + Export: + Name: !Sub '${AWS::StackName}-PublicSubnet4ID' + PublicSubnetRouteTable: + Value: !Ref PublicSubnetRouteTable + Description: Public subnet route table. + Export: + Name: !Sub '${AWS::StackName}-PublicSubnetRouteTable' + PrivateSubnet1CIDR: + Condition: PrivateSubnets + Description: Private subnet 1 CIDR in Availability Zone 1. + Value: !Ref PrivateSubnet1CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet1CIDR' + PrivateSubnet1ID: + Condition: PrivateSubnets + Description: Private subnet 1 ID in Availability Zone 1. + Value: !Ref PrivateSubnet1 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet1ID' + PrivateSubnet2CIDR: + Condition: 2AZsPrivateSubnets + Description: Private subnet 2 CIDR in Availability Zone 2. + Value: !Ref PrivateSubnet2CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet2CIDR' + PrivateSubnet2ID: + Condition: 2AZsPrivateSubnets + Description: Private subnet 2 ID in Availability Zone 2. + Value: !Ref PrivateSubnet2 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet2ID' + PrivateSubnet3CIDR: + Condition: 3AZsPrivateSubnets + Description: Private subnet 3 CIDR in Availability Zone 3. + Value: !Ref PrivateSubnet3CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet3CIDR' + PrivateSubnet3ID: + Condition: 3AZsPrivateSubnets + Description: Private subnet 3 ID in Availability Zone 3. + Value: !Ref PrivateSubnet3 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet3ID' + PrivateSubnet4CIDR: + Condition: 4AZsPrivateSubnets + Description: Private subnet 4 CIDR in Availability Zone 4. + Value: !Ref PrivateSubnet4CIDR + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet4CIDR' + PrivateSubnet4ID: + Condition: 4AZsPrivateSubnets + Description: Private subnet 4 ID in Availability Zone 4. + Value: !Ref PrivateSubnet4 + Export: + Name: !Sub '${AWS::StackName}-PrivateSubnet4ID' + AttachmentSubnet1CIDR: + Condition: AttachmentSubnets + Description: Attachment subnet 1 CIDR in Availability Zone 1. + Value: !Ref AttachmentSubnet1CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet1CIDR' + AttachmentSubnet1ID: + Condition: AttachmentSubnets + Description: Attachment subnet 1 ID in Availability Zone 1. + Value: !Ref AttachmentSubnet1 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet1ID' + AttachmentSubnet2CIDR: + Condition: 2AZsAttachmentSubnets + Description: Attachment subnet 2 CIDR in Availability Zone 2. + Value: !Ref AttachmentSubnet2CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet2CIDR' + AttachmentSubnet2ID: + Condition: 2AZsAttachmentSubnets + Description: Attachment subnet 2 ID in Availability Zone 2. + Value: !Ref AttachmentSubnet2 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet2ID' + AttachmentSubnet3CIDR: + Condition: 3AZsAttachmentSubnets + Description: Attachment subnet 3 CIDR in Availability Zone 3. + Value: !Ref AttachmentSubnet3CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet3CIDR' + AttachmentSubnet3ID: + Condition: 3AZsAttachmentSubnets + Description: Attachment subnet 3 ID in Availability Zone 3. + Value: !Ref AttachmentSubnet3 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet3ID' + AttachmentSubnet4CIDR: + Condition: 4AZsAttachmentSubnets + Description: Attachment subnet 4 CIDR in Availability Zone 4. + Value: !Ref AttachmentSubnet4CIDR + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet4CIDR' + AttachmentSubnet4ID: + Condition: 4AZsAttachmentSubnets + Description: Attachment subnet 4 ID in Availability Zone 4. + Value: !Ref AttachmentSubnet4 + Export: + Name: !Sub '${AWS::StackName}-AttachmentSubnet4ID' + IGWID: + Description: IGW ID. + Value: !Join ['', [!Ref InternetGateway]] + Export: + Name: !Sub '${AWS::StackName}-IGWID' \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster-master/README.md b/deprecated/terraform/ali/R81/cluster-master/README.md new file mode 100755 index 00000000..9ad12ed3 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster-master/README.md @@ -0,0 +1,174 @@ +# Check Point CloudGuard Network Security Cluster Master Terraform module for AliCloud + +Terraform module which deploys a Check Point CloudGuard Network Security Cluster into a new VPC. + +These types of Terraform resources are supported: +* [Security group](https://www.terraform.io/docs/providers/alicloud/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/alicloud/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/alicloud/r/eip.html) - conditional creation +* [Route_entry](https://www.terraform.io/docs/providers/alicloud/r/route_entry.html) - Internal default route: conditional creation +* [Instance](https://www.terraform.io/docs/providers/alicloud/r/instance.html) - Gateway Instances +* [RAM Role](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs/resources/ram_role) + +## Note +- Make sure your region and zone are supporting the gateway instance types in **modules/common/instance_type/main.tf** + [Alicloud Instance_By_Region](https://ecs-buy.aliyun.com/instanceTypes/?spm=a2c63.p38356.879954.139.1eeb2d44eZQw2m#/instanceTypeByRegion) + +## Configuration + +- Due to a terraform limitation, apply command is: +``` +terraform apply -target=alicloud_route_table.private_vswitch_rt -auto-approve && terraform apply +``` +>Once terraform is updated, we will update accordingly. + +- Best practice is to configure credentials in the Environment variables - [Alicloud provider](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs) +``` +Configure environment variables in Linux: + +$ export ALICLOUD_ACCESS_KEY=anaccesskey +$ export ALICLOUD_SECRET_KEY=asecretkey +$ export ALICLOUD_REGION=cn-beijing + +Configure envrionment variables in Windows: + set ALICLOUD_ACCESS_KEY=anaccesskey + set ALICLOUD_SECRET_KEY=asecretkey + set ALICLOUD_REGION=cn-beijing + +``` + +## Usage +- Fill all variables in the cluster-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + terraform init +- Create an execution plan: + terraform plan -target=alicloud_route_table.private_vswitch_rt -auto-approve && terraform plan +- Create or modify the deployment: + terraform apply -target=alicloud_route_table.private_vswitch_rt -auto-approve && terraform apply + +### terraform.tfvars variables: + +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_name | (Optional) The name of the VPC | string | n/a | "cp-vpc" | no | +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| cluster_vswitchs_map | A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| management_vswitchs_map | A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_vswitchs_map | A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| vswitchs_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a vswitchs_bit_length value of 4, the resulting vswitch address will have length /20. | number | n/a | n/a | yes | +| gateway_name | (optional) The name tag of the Cluster's Security Gateway instances | string | n/a | "Check-Point-Cluster-tf" | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - ecs.g5ne.large
- ecs.g5ne.xlarge
- ecs.g5ne.2xlarge
- ecs.g5ne.4xlarge
- ecs.g5ne.8xlarge
- ecs.g7ne.large
- ecs.g7ne.xlarge
- ecs.g7ne.2xlarge
- ecs.g7ne.4xlarge
- ecs.g7ne.8xlarge | "ecs.g5ne.xlarge" | no | +| key_name | The ECS Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to TRUE, an elastic IP will be allocated and associated with each cluster member, in addition to the cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| disk_category | The ECS disk category | string | - cloud
- cloud_efficiency
- cloud_ssd,
- cloud_essd | "cloud_efficiency" | no | +| ram_role_name | A predefined RAM role name to attach to the cluster's security gateway instances | string | n/a | "" | no | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway ECS Instances | map(string) | n/a | {}} | no | +| gateway_version | Gateway version and license | string | R81-BYOL | R81-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration. | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | "/etc/cli.sh" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | n/a | yes | +| gateway_password_hash | (optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| management_ip_address | (Optional) The Security Management IP address (public or private IP address). If provided, a static-route [management_ip --> via eth1] will be added to the Cluster's Security Gateway instances. If not provided, the static-route will need to be added manually post-deployment by user | string | n/a | "" | no | +| resources_tag_name | (optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | n/a | true | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (optional) | string | n/a | "ntp1.cloud.aliyuncs.com" | no | +| secondary_ntp | (optional) | string | n/a | "ntp2.cloud.aliyuncs.com" | no | + +## Example for terraform.tfvars + +``` +// --- VPC Network Configuration --- +vpc_name = "cp-vpc" +vpc_cidr = "10.0.0.0/16" +cluster_vswitchs_map = { + "us-east-1a" = 1 +} +management_vswitchs_map = { + "us-east-1a" = 2 +} +private_vswitchs_map = { + "us-east-1a" = 3 +} +vswitchs_bit_length = 8 + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "ecs.g5ne.large" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +management_ip_address = "1.2.3.4" +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +``` +## Conditional creation +- To create an Elastic IP for each Cluster member and associate it to the Security Gateway instances: +``` +allocate_and_associate_eip = true +``` +- To create a cluster RAM role for your Cluster instances with the required permissions for Cluster behavior, leave the ram_role_name variable empty: +``` +ram_role_name = "" +``` + +## Outputs +| Name | Description | +|----------------------------------|------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| internal_rt_id | The internal route table id id | +| vpc_cluster_vswitchs_ids_list | A list of the cluster vswitchs ids | +| vpc_management_vswitchs_ids_list | A list of the management vswitchs ids | +| vpc_private_vswitchs_ids_list | A list of the private vswitchs ids | +| image_id | The image id of the deployed Security Gateways | +| cluster_primary_EIP | Cluster Primary EIP | +| cluster_secondary_EIP | Cluster secondary EIP | +| member_a_EIP | Member A instance EIP | +| member_b_EIP | Member B instance EIP | +| member_a_instance_id | Member A instance id | +| member_b_instance_id | Member B instance id | +| member_a_instance_name | Member A instance name | +| member_b_instance_name | Member B instance name | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group name | + +## Revision History + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20230829 | Change default Check Point version to R81.20 | +| 20230615 | - Improved userdata quality and stability by moving to cloud-config
- Define default primary and secondary NTP servers
- Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230420 | Change alicloud terraform provider version to 1.203.0 | +| 20230330 | - Added support of ECS disk category.
- Stability fixes. | +| 20230329 | First release of R81.20 & R81.10 CloudGuard Gateway Terraform deployment in Alibaba Cloud and added support for g7ne instance type. | +| 20211011 | First release of Check Point CloudGuard Cluster Terraform deployment into a new VPC in Alibaba cloud. | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../LICENSE) file for details diff --git a/deprecated/terraform/ali/R81/cluster-master/locals.tf b/deprecated/terraform/ali/R81/cluster-master/locals.tf new file mode 100755 index 00000000..58775cec --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster-master/locals.tf @@ -0,0 +1,28 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster-master/main.tf b/deprecated/terraform/ali/R81/cluster-master/main.tf new file mode 100755 index 00000000..41bb165d --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster-master/main.tf @@ -0,0 +1,53 @@ +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_name = var.vpc_name + vpc_cidr = var.vpc_cidr + public_vswitchs_map = var.cluster_vswitchs_map + management_vswitchs_map = var.management_vswitchs_map + private_vswitchs_map = var.private_vswitchs_map + vswitchs_bit_length = var.vswitchs_bit_length +} + +resource "alicloud_route_table" "private_vswitch_rt" { + depends_on = [module.launch_vpc] + route_table_name = "Internal_Route_Table" + vpc_id = module.launch_vpc.vpc_id +} +resource "alicloud_route_table_attachment" "private_rt_to_private_vswitchs" { + depends_on = [module.launch_vpc, alicloud_route_table.private_vswitch_rt] + route_table_id = alicloud_route_table.private_vswitch_rt.id + vswitch_id = module.launch_vpc.private_vswitchs_ids_list[0] +} + +module "launch_cluster_into_vpc" { + source = "../cluster" + + vpc_id = module.launch_vpc.vpc_id + cluster_vswitch_id = module.launch_vpc.public_vswitchs_ids_list[0] + mgmt_vswitch_id = module.launch_vpc.management_vswitchs_ids_list[0] + private_vswitch_id = module.launch_vpc.private_vswitchs_ids_list[0] + private_route_table = alicloud_route_table.private_vswitch_rt.id + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + disk_category = var.disk_category + ram_role_name = var.ram_role_name + instance_tags = var.instance_tags + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + management_ip_address = var.management_ip_address + memberAToken = var.memberAToken + memberBToken = var.memberBToken + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster-master/output.tf b/deprecated/terraform/ali/R81/cluster-master/output.tf new file mode 100755 index 00000000..25347ba0 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster-master/output.tf @@ -0,0 +1,48 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "internal_rt_id" { + value = alicloud_route_table.private_vswitch_rt.id +} +output "vpc_cluster_vswitchs_ids_list" { + value = module.launch_vpc.public_vswitchs_ids_list +} +output "vpc_management_vswitchs_ids_list" { + value = module.launch_vpc.management_vswitchs_ids_list +} +output "vpc_private_vswitchs_ids_list" { + value = module.launch_vpc.private_vswitchs_ids_list +} +output "image_id" { + value = module.launch_cluster_into_vpc.image_id +} +output "cluster_primary_EIP" { + value = module.launch_cluster_into_vpc.cluster_primary_EIP +} +output "cluster_secondary_EIP" { + value = module.launch_cluster_into_vpc.cluster_secondary_EIP +} +output "member_a_EIP" { + value = module.launch_cluster_into_vpc.member_a_EIP +} +output "member_b_EIP" { + value = module.launch_cluster_into_vpc.member_b_EIP +} +output "member_a_instance_id" { + value = module.launch_cluster_into_vpc.member_a_instance_id +} +output "member_b_instance_id" { + value = module.launch_cluster_into_vpc.member_b_instance_id +} +output "member_a_instance_name" { + value = module.launch_cluster_into_vpc.member_a_instance_name +} +output "member_b_instance_name" { + value = module.launch_cluster_into_vpc.member_b_instance_name +} +output "permissive_sg_id" { + value = module.launch_cluster_into_vpc.permissive_sg_id +} +output "permissive_sg_name" { + value = module.launch_cluster_into_vpc.permissive_sg_name +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster-master/terraform.tfvars b/deprecated/terraform/ali/R81/cluster-master/terraform.tfvars new file mode 100755 index 00000000..42dd5743 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster-master/terraform.tfvars @@ -0,0 +1,47 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_name = "cp-vpc" +vpc_cidr = "10.0.0.0/16" +cluster_vswitchs_map = { + "us-east-1a" = 1 +} +management_vswitchs_map = { + "us-east-1a" = 2 +} +private_vswitchs_map = { + "us-east-1a" = 3 +} +vswitchs_bit_length = 8 + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "ecs.g5ne.large" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +management_ip_address = "1.2.3.4" +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" diff --git a/deprecated/terraform/ali/R81/cluster-master/variables.tf b/deprecated/terraform/ali/R81/cluster-master/variables.tf new file mode 100755 index 00000000..c20366aa --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster-master/variables.tf @@ -0,0 +1,150 @@ +// --- VPC Network Configuration --- +variable "vpc_name" { + type = string + description = "The name of the VPC" + default = "cp-vpc" +} +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "cluster_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "management_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " +} +variable "private_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " +} +variable "vswitchs_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a vswitchs_bit_length value is 4, the resulting vswitch address will have length /20" +} + +// --- ECS Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Cluster's Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" +default = "ecs.g5ne.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The ECS Key Pair name to allow SSH access to the instances" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to TRUE, an elastic IP will be allocated and associated with each cluster member, in addition to the cluster Elastic IP" +default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" +default = 100 +} +variable "disk_category" { + type = string + description = "(Optional) Category of the ECS disk" + default = "cloud_efficiency" +} +variable "ram_role_name" { + type = string + description = "A predefined RAM role name to attach to the cluster's security gateway instances" + default = "" +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway ECS Instances" +default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" +default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash)" +default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +// --- Advanced Settings --- +variable "management_ip_address" { + type = string + description = "(Optional) The Security Management IP address (public or private IP address). If provided, a static-route [management_ip --> via eth1] will be added to the Cluster's Security Gateway instances. If not provided, the static-route will need to be added manually post-deployment by user" + default = "" +} +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" +default = true +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster-master/versions.tf b/deprecated/terraform/ali/R81/cluster-master/versions.tf new file mode 100755 index 00000000..71e9843e --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster-master/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} diff --git a/deprecated/terraform/ali/R81/cluster/README.md b/deprecated/terraform/ali/R81/cluster/README.md new file mode 100755 index 00000000..5523b388 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/README.md @@ -0,0 +1,158 @@ +# Check Point CloudGuard Network Security Cluster Terraform module for AliCloud + +Terraform module which deploys a Check Point CloudGuard Network Security Cluster into an existing VPC. + +These types of Terraform resources are supported: +* [Security group](https://www.terraform.io/docs/providers/alicloud/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/alicloud/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/alicloud/r/eip.html) - conditional creation +* [Route_entry](https://www.terraform.io/docs/providers/alicloud/r/route_entry.html) - Internal default route: conditional creation +* [Instance](https://www.terraform.io/docs/providers/alicloud/r/instance.html) - Gateway Instances +* [RAM Role](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs/resources/ram_role) + +## Note +- Make sure your region and zone are supporting the gateway instance types in **modules/common/instance_type/main.tf** + [Alicloud Instance_By_Region](https://ecs-buy.aliyun.com/instanceTypes/?spm=a2c63.p38356.879954.139.1eeb2d44eZQw2m#/instanceTypeByRegion) + +## Configuration +- Best practice is to configure credentials in the Environment variables - [Alicloud provider](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs) +``` +Configure environment variables in Linux: + +$ export ALICLOUD_ACCESS_KEY=anaccesskey +$ export ALICLOUD_SECRET_KEY=asecretkey +$ export ALICLOUD_REGION=cn-beijing + +Configure envrionment variables in Windows: + set ALICLOUD_ACCESS_KEY=anaccesskey + set ALICLOUD_SECRET_KEY=asecretkey + set ALICLOUD_REGION=cn-beijing + +``` + +## Usage +- Fill all variables in the cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + terraform init +- Create an execution plan: + terraform plan +- Create or modify the deployment: + terraform apply + + +### terraform.tfvars variables: +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| cluster_vswitch_id | The cluster vswitch of the security gateways | string | Subnet in the same availability zone with mgmt_vswitch_id and private_vswitch_id | n/a | yes | +| mgmt_vswitch_id | The management vswitch of the security gateways Connect the Security Gateways to the Management Server with the ENI in this vswitch. | string | Subnet in the same availability zone with cluster_vswitch_id and private_vswitch_id | n/a | yes | +| private_vswitch_id | The private vswitch of the security gateways | string | Subnet in the same availability zone with cluster_vswitch_id and mgmt_vswitch_id | n/a | yes | +| private_route_table | (optional) Sets '0.0.0.0/0' route to the Active Cluster member instance in the specified route table (e.g. vtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Gateway, this requires manual configuration in the Route Table. | string | n/a | "" | no | +| gateway_name | (optional) The name tag of the Cluster's Security Gateway instances | string | n/a | "Check-Point-Cluster-tf" | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - ecs.g5ne.large
- ecs.g5ne.xlarge
- ecs.g5ne.2xlarge
- ecs.g5ne.4xlarge
- ecs.g5ne.8xlarge
- ecs.g7ne.large
- ecs.g7ne.xlarge
- ecs.g7ne.2xlarge
- ecs.g7ne.4xlarge
- ecs.g7ne.8xlarge | "ecs.g5ne.xlarge" | no | +| key_name | The ECS Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to TRUE, an elastic IP will be allocated and associated with each cluster member, in addition to the cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| disk_category | The ECS disk category | string | - cloud
- cloud_efficiency
- cloud_ssd,
- cloud_essd | "cloud_efficiency" | no | +| ram_role_name | A predefined RAM role name to attach to the cluster's security gateway instances | string | n/a | "" | no | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway ECS Instances | map(string) | n/a | {} | no | +| gateway_version | Gateway version and license | string | R81-BYOL | R81-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration. | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | "/etc/cli.sh" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | n/a | yes | +| gateway_password_hash | (optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| management_ip_address | (Optional) The Security Management IP address (public or private IP address). If provided, a static-route [management_ip --> via eth1] will be added to the Cluster's Security Gateway instances. If not provided, the static-route will need to be added manually post-deployment by user | string | n/a | "" | no | +| resources_tag_name | (optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (optional) The host name will be appended with member-a/b accordingly | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | n/a | true | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (optional) | string | n/a | "ntp1.cloud.aliyuncs.com" | no | +| secondary_ntp | (optional) | string | n/a | "ntp2.cloud.aliyuncs.com" | no | + +## Example for terraform.tfvars +``` +// --- VPC Network Configuration --- +vpc_id = "vpc-" +cluster_vswitch_id = "vsw-" +mgmt_vswitch_id = "vsw-" +private_vswitch_id = "vsw-" +private_route_table = "vtb-" + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "ecs.g5ne.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.10-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +management_ip_address = "1.2.3.4" +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +``` + +## Conditional creation +- To create an Elastic IP for each Cluster member and associate it to the Security Gateway instances: +``` +allocate_and_associate_eip = true +``` +- To create a default route to the Active Cluster member, fill the private_route_table variable: +``` +private_route_table = "rtb-12345678" +``` +- To create a cluster RAM role for your Cluster instances with the required permissions for Cluster behavior, leave the ram_role_name variable empty: +``` +ram_role_name = "" +``` + +## Outputs +| Name | Description | +|------------------------|------------------------------------------------| +| cluster_primary_EIP | Cluster Primary EIP | +| cluster_secondary_EIP | Cluster secondary EIP | +| image_id | The image id of the deployed Security Gateways | +| member_a_EIP | Member A instance EIP | +| member_b_EIP | Member B instance EIP | +| member_a_instance_id | Member A instance id | +| member_b_instance_id | Member B instance id | +| member_a_instance_name | Member A instance name | +| member_b_instance_name | Member B instance name | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group name | + +## Revision History + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20230829 | Change default version to R81.20 | +| 20230615 | - Improved userdata quality and stability by moving to cloud-config
- Define default primary and secondary NTP servers
- Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230420 | Change alicloud terraform provider version to 1.203.0 | +| 20230330 | - Added support of ECS disk category.
- Stability fixes. | +| 20230329 | First release of R81.20 & R81.10 CloudGuard Gateway Terraform deployment in Alibaba Cloud and added support for g7ne instance type. | +| 20211011 | First release of Check Point CloudGuard Cluster Terraform deployment into an existing VPC in Alibaba cloud. | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../LICENSE) file for details diff --git a/deprecated/terraform/ali/R81/cluster/cluster_member_a_userdata.yaml b/deprecated/terraform/ali/R81/cluster/cluster_member_a_userdata.yaml new file mode 100755 index 00000000..06dcd99f --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/cluster_member_a_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py managementIpAddress=\"${ManagementIpAddress}\" sicKey=\"${SICKey}\" installationType=\"cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20230615\" templateName=\"cluster\" templateType=\"terraform\" shell=\"${Shell}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" "smart1CloudToken=\"${TokenA}\"" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster/cluster_member_b_userdata.yaml b/deprecated/terraform/ali/R81/cluster/cluster_member_b_userdata.yaml new file mode 100755 index 00000000..20cc6e30 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/cluster_member_b_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py managementIpAddress=\"${ManagementIpAddress}\" sicKey=\"${SICKey}\" installationType=\"cluster\" osVersion=\"{OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20230615\" templateName=\"cluster\" templateType=\"terraform\" shell=\"${Shell}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" "smart1CloudToken=\"${TokenB}\"" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster/locals.tf b/deprecated/terraform/ali/R81/cluster/locals.tf new file mode 100755 index 00000000..89314651 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/locals.tf @@ -0,0 +1,46 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + //TokenA: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenA = split(" ", var.memberAToken) + tokenA_decode = base64decode(element(local.split_tokenA, length(local.split_tokenA)-1)) + regex_tokenA = regex(local.regex_token_valid, local.tokenA_decode) == local.tokenA_decode ? 0 : "Smart-1 Cloud token A is invalid format" + + //TokenB: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenB = split(" ", var.memberBToken) + tokenB_decode = base64decode(element(local.split_tokenB, length(local.split_tokenB)-1)) + regex_tokenB = regex(local.regex_token_valid, local.tokenB_decode) == local.tokenB_decode ? 0 : "Smart-1 Cloud token B is invalid format" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + + // Create RAM Role only if input variable ram_role_name was not provided + create_ram_role = var.ram_role_name == "" ? 1 : 0 + version_split = element(split("-", var.gateway_version), 0) + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) + gateway_password_hash_base64 = base64encode(var.gateway_password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster/main.tf b/deprecated/terraform/ali/R81/cluster/main.tf new file mode 100755 index 00000000..db2d9c93 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/main.tf @@ -0,0 +1,178 @@ +module "images" { + source = "../modules/images" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +// Instances +resource "alicloud_instance" "member-a-instance" { + instance_name = format("%s-Member-A", var.gateway_name) + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.images.image_id + vswitch_id = var.cluster_vswitch_id + security_groups = [ + module.common_permissive_sg.permissive_sg_id] + system_disk_size = var.volume_size + system_disk_category = var.disk_category + + tags = merge({ + Name = format("%s-Member-A", var.gateway_name) + }, var.instance_tags) + + user_data = templatefile("${path.module}/cluster_member_a_userdata.yaml", { + // script's arguments + Hostname = format("%s-member-a", var.gateway_hostname), + PasswordHash = local.gateway_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenA = var.memberAToken, + ManagementIpAddress = var.management_ip_address, + OsVersion = local.version_split + }) +} +resource "alicloud_instance" "member-b-instance" { + instance_name = format("%s-Member-B", var.gateway_name) + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.images.image_id + vswitch_id = var.cluster_vswitch_id + security_groups = [ + module.common_permissive_sg.permissive_sg_id] + system_disk_size = var.volume_size + system_disk_category = var.disk_category + + tags = merge({ + Name = format("%s-Member-B", var.gateway_name) + }, var.instance_tags) + + user_data = templatefile("${path.module}/cluster_member_b_userdata.yaml", { + // script's arguments + Hostname = format("%s-member-b", var.gateway_hostname), + PasswordHash = local.gateway_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenB = var.memberBToken, + ManagementIpAddress = var.management_ip_address, + OsVersion = local.version_split + }) +} + +// Management ENIs +resource "alicloud_network_interface" "member_a_mgmt_eni" { + network_interface_name = format("%s-Member-A-management-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) + vswitch_id = var.mgmt_vswitch_id + security_group_ids = [ + module.common_permissive_sg.permissive_sg_id] + description = "eth2" +} +resource "alicloud_network_interface_attachment" "member_a_mgmt_eni_attachment" { + instance_id = alicloud_instance.member-a-instance.id + network_interface_id = alicloud_network_interface.member_a_mgmt_eni.id +} +resource "alicloud_network_interface" "member_b_mgmt_eni" { + network_interface_name = format("%s-Member-B-management-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) + vswitch_id = var.mgmt_vswitch_id + security_group_ids = [ + module.common_permissive_sg.permissive_sg_id] + description = "eth2" +} +resource "alicloud_network_interface_attachment" "member_b_mgmt_eni_attachment" { + instance_id = alicloud_instance.member-b-instance.id + network_interface_id = alicloud_network_interface.member_b_mgmt_eni.id +} + +// Internal ENIs +resource "alicloud_network_interface" "member_a_internal_eni" { + depends_on = [alicloud_network_interface_attachment.member_a_mgmt_eni_attachment] + network_interface_name = format("%s-Member-A-internal-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) + vswitch_id = var.private_vswitch_id + security_group_ids = [ + module.common_permissive_sg.permissive_sg_id] + description = "eth2" +} +resource "alicloud_network_interface_attachment" "member_a_internal_eni_attachment" { + instance_id = alicloud_instance.member-a-instance.id + network_interface_id = alicloud_network_interface.member_a_internal_eni.id +} +resource "alicloud_network_interface" "member_b_internal_eni" { + depends_on = [alicloud_network_interface_attachment.member_b_mgmt_eni_attachment] + network_interface_name = format("%s-Member-B-internal-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) + vswitch_id = var.private_vswitch_id + security_group_ids = [ + module.common_permissive_sg.permissive_sg_id] + description = "eth2" +} +resource "alicloud_network_interface_attachment" "member_b_internal_eni_attachment" { + instance_id = alicloud_instance.member-b-instance.id + network_interface_id = alicloud_network_interface.member_b_internal_eni.id +} + +// EIPs +module "common_cluster_primary_eip" { + source = "../modules/common/elastic_ip" + + allocate_and_associate_eip = true + instance_id = alicloud_instance.member-a-instance.id + eip_name = format("%s-cluster-primary-eip", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) +} +module "common_cluster_secondary_eip" { + source = "../modules/common/elastic_ip" + + allocate_and_associate_eip = true + instance_id = alicloud_instance.member-b-instance.id + eip_name = format("%s-cluster-secondary-eip", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) +} +module "common_member_a_mgmt_eip" { + source = "../modules/common/elastic_ip" + + allocate_and_associate_eip = var.allocate_and_associate_eip + instance_id = alicloud_network_interface.member_a_mgmt_eni.id + association_instance_type = "NetworkInterface" + eip_name = format("%s-member-A-eip", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) +} +module "common_member_b_mgmt_eip" { + source = "../modules/common/elastic_ip" + + allocate_and_associate_eip = var.allocate_and_associate_eip + instance_id = alicloud_network_interface.member_b_mgmt_eni.id + association_instance_type = "NetworkInterface" + eip_name = format("%s-member-B-eip", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) +} + +module "common_internal_default_route" { + source = "../modules/common/internal_default_route" + + private_route_table = var.private_route_table + internal_eni_id = alicloud_network_interface.member_a_internal_eni.id +} + +module "cluster_ram_role" { + count = local.create_ram_role + source = "../modules/cluster-ram-role" + + gateway_name = var.gateway_name +} + +resource "alicloud_ram_role_attachment" "attach" { + depends_on = [alicloud_instance.member-a-instance, alicloud_instance.member-b-instance] + role_name = var.ram_role_name != "" ? var.ram_role_name : module.cluster_ram_role[0].cluster_ram_role_name + instance_ids = [alicloud_instance.member-a-instance.id, alicloud_instance.member-b-instance.id] +} diff --git a/deprecated/terraform/ali/R81/cluster/output.tf b/deprecated/terraform/ali/R81/cluster/output.tf new file mode 100755 index 00000000..623cca8f --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/output.tf @@ -0,0 +1,33 @@ +output "cluster_primary_EIP" { + value = module.common_cluster_primary_eip.instance_eip_public_ip[0] +} +output "cluster_secondary_EIP" { + value = module.common_cluster_secondary_eip.instance_eip_public_ip[0] +} +output "image_id" { + value = module.images.image_id +} +output "member_a_EIP" { + value = module.common_member_a_mgmt_eip.instance_eip_public_ip[0] +} +output "member_b_EIP" { + value = module.common_member_b_mgmt_eip.instance_eip_public_ip[0] +} +output "member_a_instance_id" { + value = alicloud_instance.member-a-instance.id +} +output "member_b_instance_id" { + value = alicloud_instance.member-b-instance.id +} +output "member_a_instance_name" { + value = alicloud_instance.member-a-instance.instance_name +} +output "member_b_instance_name" { + value = alicloud_instance.member-b-instance.instance_name +} +output "permissive_sg_id" { + value = module.common_permissive_sg.permissive_sg_id +} +output "permissive_sg_name" { + value = module.common_permissive_sg.permissive_sg_name +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster/terraform.tfvars b/deprecated/terraform/ali/R81/cluster/terraform.tfvars new file mode 100755 index 00000000..35d0209a --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/terraform.tfvars @@ -0,0 +1,40 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-" +cluster_vswitch_id = "vsw-" +mgmt_vswitch_id = "vsw-" +private_vswitch_id = "vsw-" +private_route_table = "vtb-" + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "ecs.g5ne.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +management_ip_address = "1.2.3.4" +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster/variables.tf b/deprecated/terraform/ali/R81/cluster/variables.tf new file mode 100755 index 00000000..51042420 --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/variables.tf @@ -0,0 +1,144 @@ +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "cluster_vswitch_id" { + type = string + description = "The cluster vswitch of the security gateways" +} +variable "mgmt_vswitch_id" { + type = string + description = "The management vswitch of the security gateways" +} +variable "private_vswitch_id" { + type = string + description = "The private vswitch of the security gateways" +} +variable "private_route_table" { + type = string + description = "(Optional) Sets '0.0.0.0/0' route to the Active Cluster member instance in the specified route table (e.g. vtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Gateway, this requires manual configuration in the Route Table" + default="" +} + +// --- ECS Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Cluster's Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "ecs.g5ne.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The ECS Key Pair name to allow SSH access to the instances" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to TRUE, an elastic IP will be allocated and associated with each cluster member, in addition to the cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +variable "disk_category" { + type = string + description = "(Optional) Category of the ECS disk" + default = "cloud_efficiency" +} +variable "ram_role_name" { + type = string + description = "A predefined RAM role name to attach to the cluster's security gateway instances" + default = "" +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway ECS Instances" + default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash)" + default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +// --- Advanced Settings --- +variable "management_ip_address" { + type = string + description = "(Optional) The Security Management IP address (public or private IP address). If provided, a static-route [management_ip --> via eth1] will be added to the Cluster's Security Gateway instances. If not provided, the static-route will need to be added manually post-deployment by user" + default = "" +} +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/cluster/versions.tf b/deprecated/terraform/ali/R81/cluster/versions.tf new file mode 100755 index 00000000..71e9843e --- /dev/null +++ b/deprecated/terraform/ali/R81/cluster/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} diff --git a/deprecated/terraform/ali/R81/gateway-master/README.md b/deprecated/terraform/ali/R81/gateway-master/README.md new file mode 100755 index 00000000..97a9d95e --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway-master/README.md @@ -0,0 +1,155 @@ +# Check Point Gateway Master Terraform module for AliCloud + +Terraform module which deploys a Check Point Security Gateway into a new VPC on AliCloud. + +These types of Terraform resources are supported: +* [Security group](https://www.terraform.io/docs/providers/alicloud/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/alicloud/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/alicloud/r/eip.html) - conditional creation +* [Route_entry](https://www.terraform.io/docs/providers/alicloud/r/route_entry.html) - Internal default route: conditional creation +* [Instance](https://www.terraform.io/docs/providers/alicloud/r/instance.html) - Gateway Instance + +## Note +- Make sure your region and zone are supporting the gateway instance types in **modules/common/instance_type/main.tf** + [Alicloud Instance_By_Region](https://ecs-buy.aliyun.com/instanceTypes/?spm=a2c63.p38356.879954.139.1eeb2d44eZQw2m#/instanceTypeByRegion) + +## Configuration + +- Due to a terraform limitation, apply command is: +``` +terraform apply -target=alicloud_route_table.private_vswitch_rt -auto-approve && terraform apply +``` +>Once terraform is updated, we will update accordingly. + +- Best practice is to configure credentials in the Environment variables - [Alicloud provider](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs) +``` +Configure environment variables in Linux: + +$ export ALICLOUD_ACCESS_KEY=anaccesskey +$ export ALICLOUD_SECRET_KEY=asecretkey +$ export ALICLOUD_REGION=cn-beijing + +Configure envrionment variables in Windows: + set ALICLOUD_ACCESS_KEY=anaccesskey + set ALICLOUD_SECRET_KEY=asecretkey + set ALICLOUD_REGION=cn-beijing + +``` + +## Usage +- Fill all variables in the gateway-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + terraform init +- Create an execution plan: + terraform plan -target=alicloud_route_table.private_vswitch_rt -auto-approve && terraform plan +- Create or modify the deployment: + terraform apply -target=alicloud_route_table.private_vswitch_rt -auto-approve && terraform apply + +### terraform.tfvars variables: + +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_name | (Optional) The name of the VPC | string | n/a | "cp-vpc" | no | +| vpc_cidr | The CIDR block of the VPC. | string | n/a | n/a | yes | +| public_vswitchs_map | A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_vswitchs_map | A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| vswitchs_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a vswitchs_bit_length value of 4, the resulting vswitch address will have length /20. | number | n/a | n/a | yes | +| gateway_name | The name tag of the Security Gateway instances (optional) | string | n/a | "Check-Point-Gateway-tf" | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - ecs.g5ne.large
- ecs.g5ne.xlarge
- ecs.g5ne.2xlarge
- ecs.g5ne.4xlarge
- ecs.g5ne.8xlarge
- ecs.g7ne.large
- ecs.g7ne.xlarge
- ecs.g7ne.2xlarge
- ecs.g7ne.4xlarge
- ecs.g7ne.8xlarge
- ecs.g7nene.large
- ecs.g7nene.xlarge
- ecs.g7nene.2xlarge
- ecs.g7nene.4xlarge
- ecs.g7nene.8xlarge | "ecs.g5ne.xlarge" | no | +| key_name | The ECS Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to TRUE, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| disk_category | The ECS disk category | string | - cloud
- cloud_efficiency
- cloud_ssd,
- cloud_essd | "cloud_efficiency" | no | +| ram_role_name | A predefined RAM role name to attach to the security gateway instance | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | R81-BYOL | R81-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration. | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | "/etc/cli.sh" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | n/a | yes | +| password_hash | Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash) (optional) | string | n/a | "" | no | +| gateway_TokenKey | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| gateway_hostname | (optional) The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | n/a | true | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (optional) | string | n/a | "ntp1.cloud.aliyuncs.com" | no | +| secondary_ntp | (optional) | string | n/a | "ntp2.cloud.aliyuncs.com" | no | + +## Example for terraform.tfvars + +``` +// --- VPC Network Configuration --- +vpc_name = "cp-vpc" +vpc_cidr = "10.0.0.0/16" +public_vswitchs_map = { + "us-east-1a" = 1 +} +private_vswitchs_map = { + "us-east-1a" = 2 +} +vswitchs_bit_length = 8 + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "ecs.g5ne.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +``` +## Conditional creation +- To create an Elastic IP and associate it to the Gateway instance: +``` +allocate_and_associate_eip = true +``` + +## Outputs +| Name | Description | +|-------------------------------|---------------------------------------------| +| vpc_id | The id of the deployed vpc | +| internal_rt_id | The internal route table id id | +| vpc_public_vswitchs_ids_list | A list of the private vswitchs ids | +| vpc_private_vswitchs_ids_list | A list of the private vswitchs ids | +| image_id | The ami id of the deployed Security Gateway | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group id name | +| gateway_eip_id | The id of the elastic IP | +| gateway_eip_public_ip | The elastic pubic IP | +| gateway_instance_id | The Security Gateway instance id | +| gateway_instance_name | The deployed Gateway AliCloud instance name | + +## Revision History + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20230829 | Change default Check Point version to R81.20 | +| 20230615 | - Improved userdata quality and stability by moving to cloud-config
- Define default primary and secondary NTP servers
- Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230420 | Change alicloud terraform provider version to 1.203.0 | +| 20230330 | - Added support of ECS disk category.
- Stability fixes. | +| 20230329 | First release of R81.20 & R81.10 CloudGuard Gateway Terraform deployment in Alibaba Cloud and added support for g7ne instance type. | +| 20211011 | First release of Check Point CloudGuard Gateway Terraform deployment into a new VPC in Alibaba cloud. | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway-master/locals.tf b/deprecated/terraform/ali/R81/gateway-master/locals.tf new file mode 100755 index 00000000..706b0458 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway-master/locals.tf @@ -0,0 +1,17 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway-master/main.tf b/deprecated/terraform/ali/R81/gateway-master/main.tf new file mode 100755 index 00000000..d2c35c1f --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway-master/main.tf @@ -0,0 +1,49 @@ +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_name = var.vpc_name + vpc_cidr = var.vpc_cidr + public_vswitchs_map = var.public_vswitchs_map + private_vswitchs_map = var.private_vswitchs_map + vswitchs_bit_length = var.vswitchs_bit_length +} + +resource "alicloud_route_table" "private_vswitch_rt" { + depends_on = [module.launch_vpc] + route_table_name = "Internal_Route_Table" + vpc_id = module.launch_vpc.vpc_id +} +resource "alicloud_route_table_attachment" "private_rt_to_private_vswitchs" { + depends_on = [module.launch_vpc, alicloud_route_table.private_vswitch_rt] + route_table_id = alicloud_route_table.private_vswitch_rt.id + vswitch_id = module.launch_vpc.private_vswitchs_ids_list[0] +} + +module "launch_gateway_into_vpc" { + source = "../gateway" + + vpc_id = module.launch_vpc.vpc_id + public_vswitch_id = module.launch_vpc.public_vswitchs_ids_list[0] + private_vswitch_id = module.launch_vpc.private_vswitchs_ids_list[0] + private_route_table = alicloud_route_table.private_vswitch_rt.id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + disk_category = var.disk_category + ram_role_name = var.ram_role_name + instance_tags = var.instance_tags + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_TokenKey = var.gateway_TokenKey + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway-master/output.tf b/deprecated/terraform/ali/R81/gateway-master/output.tf new file mode 100755 index 00000000..ed33d983 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway-master/output.tf @@ -0,0 +1,33 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "internal_rt_id" { + value = alicloud_route_table.private_vswitch_rt.id +} +output "vpc_public_vswitchs_ids_list" { + value = module.launch_vpc.public_vswitchs_ids_list +} +output "vpc_private_vswitchs_ids_list" { + value = module.launch_vpc.private_vswitchs_ids_list +} +output "image_id" { + value = module.launch_gateway_into_vpc.image_id +} +output "permissive_sg_id" { + value = module.launch_gateway_into_vpc.permissive_sg_id +} +output "permissive_sg_name" { + value = module.launch_gateway_into_vpc.permissive_sg_name +} +output "gateway_eip_id" { + value = module.launch_gateway_into_vpc.gateway_eip_id +} +output "gateway_eip_public_ip" { + value = module.launch_gateway_into_vpc.gateway_eip_public_ip +} +output "gateway_instance_id" { + value = module.launch_gateway_into_vpc.gateway_instance_id +} +output "gateway_instance_name" { + value = module.launch_gateway_into_vpc.gateway_instance_name +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway-master/terraform.tfvars b/deprecated/terraform/ali/R81/gateway-master/terraform.tfvars new file mode 100755 index 00000000..c43d3d8d --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway-master/terraform.tfvars @@ -0,0 +1,42 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_name = "cp-vpc" +vpc_cidr = "10.0.0.0/16" +public_vswitchs_map = { + "us-east-1a" = 1 +} +private_vswitchs_map = { + "us-east-1a" = 2 +} +vswitchs_bit_length = 8 + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "ecs.g5ne.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" diff --git a/deprecated/terraform/ali/R81/gateway-master/variables.tf b/deprecated/terraform/ali/R81/gateway-master/variables.tf new file mode 100755 index 00000000..68b88ac6 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway-master/variables.tf @@ -0,0 +1,140 @@ +// --- VPC Network Configuration --- +variable "vpc_name" { + type = string + description = "The name of the VPC" + default = "cp-vpc" +} +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "vswitchs_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a vswitchs_bit_length value is 4, the resulting vswitch address will have length /20" +} + +// --- ECS Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" +default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Secutiry Gateways" +default = "ecs.g5ne.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The ECS Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to TRUE, an elastic IP will be allocated and associated with the launched instance" +default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" +default = 100 +} +variable "disk_category" { + type = string + description = "(Optional) Category of the ECS disk" + default = "cloud_efficiency" +} +variable "ram_role_name" { + type = string + description = "RAM role name to attach to the instance profile" + default = "" +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway ECS Instance" +default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" +default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash)" +default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional)" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" +default = true +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway-master/versions.tf b/deprecated/terraform/ali/R81/gateway-master/versions.tf new file mode 100755 index 00000000..71e9843e --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway-master/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} diff --git a/deprecated/terraform/ali/R81/gateway/README.md b/deprecated/terraform/ali/R81/gateway/README.md new file mode 100755 index 00000000..0c4c79b1 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway/README.md @@ -0,0 +1,141 @@ +# Check Point Gateway Terraform module for AliCloud + +Terraform module which deploys a Check Point Security Gateway into an existing VPC. + +These types of Terraform resources are supported: +* [Security group](https://www.terraform.io/docs/providers/alicloud/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/alicloud/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/alicloud/r/eip.html) - conditional creation +* [Route_entry](https://www.terraform.io/docs/providers/alicloud/r/route_entry.html) - Internal default route: conditional creation +* [Instance](https://www.terraform.io/docs/providers/alicloud/r/instance.html) - Gateway Instance + +## Note +- Make sure your region and zone are supporting the gateway instance types in **modules/common/instance_type/main.tf** + [Alicloud Instance_By_Region](https://ecs-buy.aliyun.com/instanceTypes/?spm=a2c63.p38356.879954.139.1eeb2d44eZQw2m#/instanceTypeByRegion) + +## Configuration +- Best practice is to configure credentials in the Environment variables - [Alicloud provider](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs) +``` +Configure environment variables in Linux: + +$ export ALICLOUD_ACCESS_KEY=anaccesskey +$ export ALICLOUD_SECRET_KEY=asecretkey +$ export ALICLOUD_REGION=cn-beijing + +Configure envrionment variables in Windows: + set ALICLOUD_ACCESS_KEY=anaccesskey + set ALICLOUD_SECRET_KEY=asecretkey + set ALICLOUD_REGION=cn-beijing + +``` + +## Usage +- Fill all variables in the gateway/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + terraform init +- Create an execution plan: + terraform plan +- Create or modify the deployment: + terraform apply + +### terraform.tfvars variables: +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| vpc_cidr | The CIDR block of the provided VPC | string | n/a | n/a | yes | +| public_vswitch_id | The public vswitch of the security gateway | string | n/a | n/a | yes | +| private_vswitch_id | The private vswitch of the security gateway | string | n/a | n/a | yes | +| private_route_table | Sets '0.0.0.0/0' route to the Gateway instance in the specified route table (e.g. rtb-12a34567) | string | n/a | "" | no | +| gateway_name | The name tag of the Security Gateway instances (optional) | string | n/a | "Check-Point-Gateway-tf" | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - ecs.g5ne.large
- ecs.g5ne.xlarge
- ecs.g5ne.2xlarge
- ecs.g5ne.4xlarge
- ecs.g5ne.8xlarge
- ecs.g7ne.large
- ecs.g7ne.xlarge
- ecs.g7ne.2xlarge
- ecs.g7ne.4xlarge
- ecs.g7ne.8xlarge | "ecs.g5ne.xlarge" | no | +| key_name | The ECS Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to TRUE, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| disk_category | The ECS disk category | string | - cloud
- cloud_efficiency
- cloud_ssd,
- cloud_essd | "cloud_efficiency" | no | +| ram_role_name | A predefined RAM role name to attach to the security gateway instance | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | R81-BYOL | R8-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration. | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | "/etc/cli.sh" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | n/a | yes | +| password_hash | Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash) (optional) | string | n/a | "" | no | +| gateway_TokenKey | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| gateway_hostname | (optional) The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | n/a | true | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (optional) | string | n/a | "ntp1.cloud.aliyuncs.com" | no | +| secondary_ntp | (optional) | string | n/a | "ntp2.cloud.aliyuncs.com" | no | + +## Example for terraform.tfvars +``` +// --- VPC Network Configuration --- +vpc_id = "vpc-" +public_vswitch_id = "vsw-" +private_vswitch_id = "vsw-" +private_route_table = "vtb-" + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "ecs.g5ne.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +``` +## Conditional creation +- To create an Elastic IP and associate it to the Gateway instance: +``` +allocate_and_associate_eip = true +``` +- To create a default route at the private route table: +``` +private_route_table = "rtb-12345678" +``` + +## Outputs +| Name | Description | +|-----------------------|-----------------------------------------------| +| image_id | The image id of the deployed Security Gateway | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group id name | +| gateway_eip_id | The id of the elastic IP | +| gateway_eip_public_ip | The elastic pubic IP | +| gateway_instance_id | The Security Gateway instance id | +| gateway_instance_name | The deployed Gateway AliCloud instance name | + +## Revision History + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20230829 | Change default Check Point version to R81.20 | +| 20230615 | - Improved userdata quality and stability by moving to cloud-config
- Define default primary and secondary NTP servers
- Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230420 | Change alicloud terraform provider version to 1.203.0 | +| 20230330 | - Added support of ECS disk category.
- Stability fixes. | +| 20230329 | First release of R81.20 & R81.10 CloudGuard Gateway Terraform deployment in Alibaba Cloud and added support for g7ne instance type. | +| 20211011 | First release of Check Point CloudGaurd Gateway Terraform deployment into an existing VPC in Alibaba cloud. | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway/locals.tf b/deprecated/terraform/ali/R81/gateway/locals.tf new file mode 100755 index 00000000..7f880dea --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway/locals.tf @@ -0,0 +1,23 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + //will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_token = split(" ", var.gateway_TokenKey) + token_decode = base64decode(element(local.split_token, length(local.split_token)-1)) + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + regex_token = regex(local.regex_token_valid, local.token_decode) == local.token_decode ? 0 : "Smart-1 Cloud token is invalid format" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway/main.tf b/deprecated/terraform/ali/R81/gateway/main.tf new file mode 100755 index 00000000..93bfb0c1 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway/main.tf @@ -0,0 +1,70 @@ +module "images" { + source = "../modules/images" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +module "common_gateway_instance" { + source = "../modules/common/gateway_instance" + security_groups = [ + module.common_permissive_sg.permissive_sg_id] + gateway_name = var.gateway_name + volume_size = var.volume_size + disk_category = var.disk_category + vswitch_id = var.public_vswitch_id + gateway_instance_type = var.gateway_instance_type + instance_tags = var.instance_tags + key_name = var.key_name + image_id = module.images.image_id + gateway_password_hash = var.gateway_password_hash + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_TokenKey = var.gateway_TokenKey + gateway_bootstrap_script = var.gateway_bootstrap_script + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + gateway_version = var.gateway_version +} + +resource "alicloud_network_interface" "internal_eni" { + network_interface_name = format("%s-internal-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) + vswitch_id = var.private_vswitch_id + security_group_ids = [ + module.common_permissive_sg.permissive_sg_id] + description = "eth1" +} + +resource "alicloud_network_interface_attachment" "internal_eni_attachment" { + instance_id = module.common_gateway_instance.gateway_instance_id + network_interface_id = alicloud_network_interface.internal_eni.id +} + +module "common_internal_default_route" { + source = "../modules/common/internal_default_route" + + private_route_table = var.private_route_table + internal_eni_id = alicloud_network_interface.internal_eni.id +} + +module "common_eip" { + source = "../modules/common/elastic_ip" + allocate_and_associate_eip = var.allocate_and_associate_eip + instance_id = module.common_gateway_instance.gateway_instance_id +} + +resource "alicloud_ram_role_attachment" "attach" { + count = var.ram_role_name != "" ? 1 : 0 + role_name = var.ram_role_name + instance_ids = [module.common_gateway_instance.gateway_instance_id] +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway/output.tf b/deprecated/terraform/ali/R81/gateway/output.tf new file mode 100755 index 00000000..7f2e85c1 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway/output.tf @@ -0,0 +1,21 @@ +output "image_id" { + value = module.images.image_id +} +output "permissive_sg_id" { + value = module.common_permissive_sg.permissive_sg_id +} +output "permissive_sg_name" { + value = module.common_permissive_sg.permissive_sg_name +} +output "gateway_eip_id" { + value = module.common_eip.instance_eip_id +} +output "gateway_eip_public_ip" { + value = module.common_eip.instance_eip_public_ip +} +output "gateway_instance_id" { + value = module.common_gateway_instance.gateway_instance_id +} +output "gateway_instance_name" { + value = module.common_gateway_instance.gateway_instance_name +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway/terraform.tfvars b/deprecated/terraform/ali/R81/gateway/terraform.tfvars new file mode 100755 index 00000000..4d02e623 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway/terraform.tfvars @@ -0,0 +1,37 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-" +public_vswitch_id = "vsw-" +private_vswitch_id = "vsw-" +private_route_table = "vtb-" + +// --- ECS Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "ecs.g5ne.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_efficiency" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway/variables.tf b/deprecated/terraform/ali/R81/gateway/variables.tf new file mode 100755 index 00000000..a141b140 --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway/variables.tf @@ -0,0 +1,133 @@ +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_vswitch_id" { + type = string + description = "The public vswitch of the security gateway" +} +variable "private_vswitch_id" { + type = string + description = "The private vswitch of the security gateway" +} +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Gateway instance in the specified route table (e.g. vtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route. If empty - traffic will not be routed through the Security Gateway, this requires manual configuration in the Route Table" +default="" +} + +// --- ECS Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Secutiry Gateways" + default = "ecs.g5ne.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The ECS Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to TRUE, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +variable "disk_category" { + type = string + description = "(Optional) Category of the ECS disk" + default = "cloud_efficiency" +} +variable "ram_role_name" { + type = string + description = "RAM role name to attach to the instance profile" + default = "" +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway ECS Instance" +default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash)" + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional)" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/gateway/versions.tf b/deprecated/terraform/ali/R81/gateway/versions.tf new file mode 100755 index 00000000..71e9843e --- /dev/null +++ b/deprecated/terraform/ali/R81/gateway/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} diff --git a/deprecated/terraform/ali/R81/management-master/README.md b/deprecated/terraform/ali/R81/management-master/README.md new file mode 100755 index 00000000..d5cf23c9 --- /dev/null +++ b/deprecated/terraform/ali/R81/management-master/README.md @@ -0,0 +1,134 @@ +# Check Point Management master Server Terraform module for AliCloud + +Terraform module which deploys a Check Point Management Server into a new VPC on AliCloud. + +These types of Terraform resources are supported: +* [Instance](https://www.terraform.io/docs/providers/alicloud/r/instance.html) - management Instance +* [Security group](https://www.terraform.io/docs/providers/alicloud/r/security_group.html) + + +## Note +- Make sure your region and zone are supporting the management instance types in **modules/common/instance_type/main.tf** + [Alicloud Instance_By_Region](https://ecs-buy.aliyun.com/instanceTypes/?spm=a2c63.p38356.879954.139.1eeb2d44eZQw2m#/instanceTypeByRegion) + +## Configuration +- Best practice is to configure credentials in the Environment variables - [Alicloud provider](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs) +``` +Configure environment variables in Linux: + +$ export ALICLOUD_ACCESS_KEY=anaccesskey +$ export ALICLOUD_SECRET_KEY=asecretkey +$ export ALICLOUD_REGION=cn-beijing + +Configure envrionment variables in Windows: + set ALICLOUD_ACCESS_KEY=anaccesskey + set ALICLOUD_SECRET_KEY=asecretkey + set ALICLOUD_REGION=cn-beijing + +``` +## Usage +- Fill all variables in the management-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + terraform init +- Create an execution plan: + terraform plan +- Create or modify the deployment: + terraform apply + +### terraform.tfvars variables: +| Name | Description | Type | Allowed values | Default | Required | +|-----------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|----------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_name | (Optional) The name of the VPC | string | n/a | "cp-vpc" | no | +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| vswitch_id | Vswitch id | string | n/a | n/a | yes | +| instance_name | AliCloud instance name to launch | string | n/a | "CP-Management-tf" | no | +| instance_type | AliCloud instance type | string | - ecs.g6e.large
- ecs.g6e.xlarge
- ecs.g6e.2xlarge
- ecs.g6e.4xlarge
- ecs.g6e.8xlarge | "ecs.g6e.xlarge" | no | +| key_name | The ECS Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| eip | Allocate and associate an elastic IP with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) | number | n/a | 100 | no | +| disk_category | The ECS disk category | string | - cloud
- cloud_efficiency
- cloud_ssd,
- cloud_essd | "cloud_essd" | no | +| ram_role_name | RAM role name to attach to the instance profile, leave it empty for automatic creation | string | n/a | "" | no | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Management ECS Instance | map(string) | n/a | {} | no | +| version_license | Version and license of the Check Point Security Management | string | R81-BYOL | R81-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| password_hash | (Optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash) | string | n/a | "" | no | +| hostname | (Optional) Management prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | n/a | no | +| is_primary_management | Determines if this is the primary Management Server or not | bool | true/false | true | no | +| SICKey | "Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | n/a | true | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, SSH, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| primary_ntp | (Optional) | string | n/a | "ntp1.cloud.aliyuncs.com" | no | +| secondary_ntp | (Optional) | string | n/a | "ntp2.cloud.aliyuncs.com" | no | +| bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | + +## Example for terraform.tfvars +``` +// --- VPC Network Configuration --- +vpc_name = "cp-vpc" +vpc_cidr = "10.0.0.0/16" +public_vswitchs_map = { + "us-east-1a" = 1 +} +vswitchs_bit_length = 8 + + +// --- ECS Instances Configuration --- +instance_name = "CP-Management-tf" +instance_type = "ecs.g6e.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_essd" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +version_license = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +password_hash = "" +hostname = "mgmt-tf" + +// --- Security Management Server Settings --- +is_primary_management = "true" +SICKey = "" +allow_upload_download = "true" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" +``` + +## Outputs +| Name | Description | +|-------------------------------|-------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| vpc_public_vswitchs_ids_list | A list of the private vswitchs ids | +| vpc_private_vswitchs_ids_list | A list of the private vswitchs ids | +| image_id | The ami id of the deployed Security Gateway | +| management_instance_id | The deployed Management AliCloud instance id | +| management_instance_name | The deployed Management AliCloud instance name | +| management_instance_tags | The deployed Management AliCloud tags | +| management_public_ip | The deployed Management AliCloud public address | + +## Revision History + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20230829 | Change default Check Point version to R81.20 | +| 20230615 | - Improved userdata quality and stability by moving to cloud-config
- Define default primary and secondary NTP servers
- Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230420 | Change alicloud terraform provider version to 1.203.0 | +| 20230330 | - Added support of ECS disk category.
- Stability fixes. | +| 20230129 | First release of R81.20 CloudGuard Management Terraform deployment in Alibaba Cloud. | +| 20211011 | First release of Check Point CloudGuard Management Terraform deployment into a new VPC in Alibaba cloud. | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management-master/locals.tf b/deprecated/terraform/ali/R81/management-master/locals.tf new file mode 100755 index 00000000..d64e0b51 --- /dev/null +++ b/deprecated/terraform/ali/R81/management-master/locals.tf @@ -0,0 +1,20 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // Will fail if var.gateway_management is invalid + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_cidr or var.gateway_addresses are invalid + mgmt_vswitch_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_cidr must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management-master/main.tf b/deprecated/terraform/ali/R81/management-master/main.tf new file mode 100755 index 00000000..1e47d448 --- /dev/null +++ b/deprecated/terraform/ali/R81/management-master/main.tf @@ -0,0 +1,40 @@ +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_name = var.vpc_name + vpc_cidr = var.vpc_cidr + public_vswitchs_map = var.public_vswitchs_map + private_vswitchs_map = {} + vswitchs_bit_length = var.vswitchs_bit_length +} + +module "launch_management_into_vpc" { + source = "../management" + + vpc_id = module.launch_vpc.vpc_id + vswitch_id = module.launch_vpc.public_vswitchs_ids_list[0] + ram_role_name = var.ram_role_name + + instance_name = var.instance_name + instance_type = var.instance_type + key_name = var.key_name + + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + disk_category = var.disk_category + instance_tags = var.instance_tags + version_license = var.version_license + admin_shell = var.admin_shell + password_hash = var.password_hash + hostname = var.hostname + is_primary_management = var.is_primary_management + SICKey = var.SICKey + allow_upload_download = var.allow_upload_download + gateway_management = var.gateway_management + admin_cidr = var.admin_cidr + gateway_addresses = var.gateway_addresses + bootstrap_script = var.bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp +} diff --git a/deprecated/terraform/ali/R81/management-master/output.tf b/deprecated/terraform/ali/R81/management-master/output.tf new file mode 100755 index 00000000..fa85cce2 --- /dev/null +++ b/deprecated/terraform/ali/R81/management-master/output.tf @@ -0,0 +1,25 @@ +output "Deployment" { + value = "Finalizing configuration may take up to 20 minutes after deployment is finished" +} + +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "vpc_public_vswitchs_ids_list" { + value = module.launch_vpc.public_vswitchs_ids_list +} +output "image_id" { + value = module.launch_management_into_vpc.image_id +} +output "management_instance_id" { + value = module.launch_management_into_vpc.management_instance_id +} +output "management_instance_name" { + value = module.launch_management_into_vpc.management_instance_name +} +output "management_instance_tags" { + value = module.launch_management_into_vpc.management_instance_tags +} +output "management_public_ip" { + value = module.launch_management_into_vpc.management_public_ip +} diff --git a/deprecated/terraform/ali/R81/management-master/terraform.tfvars b/deprecated/terraform/ali/R81/management-master/terraform.tfvars new file mode 100755 index 00000000..bf6cb990 --- /dev/null +++ b/deprecated/terraform/ali/R81/management-master/terraform.tfvars @@ -0,0 +1,40 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_name = "cp-vpc" +vpc_cidr = "10.0.0.0/16" +public_vswitchs_map = { + "us-east-1a" = 1 +} +vswitchs_bit_length = 8 + + +// --- ECS Instances Configuration --- +instance_name = "CP-Management-tf" +instance_type = "ecs.g6e.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_essd" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +version_license = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +password_hash = "" +hostname = "mgmt-tf" + +// --- Security Management Server Settings --- +is_primary_management = "true" +SICKey = "" +allow_upload_download = "true" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" diff --git a/deprecated/terraform/ali/R81/management-master/variables.tf b/deprecated/terraform/ali/R81/management-master/variables.tf new file mode 100755 index 00000000..aa9954f7 --- /dev/null +++ b/deprecated/terraform/ali/R81/management-master/variables.tf @@ -0,0 +1,137 @@ +// --- VPC Network Configuration --- +variable "vpc_name" { + type = string + description = "The name of the VPC" + default = "cp-vpc" +} +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "vswitchs_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a vswitchs_bit_length value is 4, the resulting vswitch address will have length /20" +} +// --- ECS Instance Configuration --- +variable "instance_name" { + type = string + description = "AliCloud instance name to launch" + default = "CP-Management-tf" +} +variable "instance_type" { + type = string + description = "" + default ="ecs.g6e.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.instance_type +} +variable "key_name" { + type = string + description = "The ECS Key Pair name to allow SSH access to the instances" +} +variable "allocate_and_associate_eip" { + type = bool + description = "When set to 'true', an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +variable "disk_category" { + type = string + description = "(Optional) Category of the ECS disk" + default = "cloud_essd" +} +variable "ram_role_name" { + type = string + description = "RAM role name to attach to the instance profile" + default = "" +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Management ECS Instance" +default = {} +} +// --- Check Point Settings --- +variable "version_license" { + type = string + description = "version and license" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.version_license +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "hostname" { + type = string + description = "(Optional)" + default = "" +} + +// --- Security Management Server Settings --- +variable "is_primary_management" { + type = bool + description = "true/false. Determines if this is the primary management server or not" + default = true +} +variable "SICKey" { + type = string + description = "Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, SSH, and graphical clients only from this network to communicate with the Management Server" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Management Server" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "" +} +variable "bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management-master/versions.tf b/deprecated/terraform/ali/R81/management-master/versions.tf new file mode 100755 index 00000000..71e9843e --- /dev/null +++ b/deprecated/terraform/ali/R81/management-master/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} diff --git a/deprecated/terraform/ali/R81/management/README.md b/deprecated/terraform/ali/R81/management/README.md new file mode 100755 index 00000000..9a46c521 --- /dev/null +++ b/deprecated/terraform/ali/R81/management/README.md @@ -0,0 +1,127 @@ +# Check Point Management Server Terraform module for AliCloud + +Terraform module which deploys a Check Point Management Server into an existing VPC on AliCloud. + +These types of Terraform resources are supported: +* [Instance](https://www.terraform.io/docs/providers/alicloud/r/instance.html) - management Instance +* [Security group](https://www.terraform.io/docs/providers/alicloud/r/security_group.html) + + +## Note +- Make sure your region and zone are supporting the management instance types in **modules/common/instance_type/main.tf** + [Alicloud Instance_By_Region](https://ecs-buy.aliyun.com/instanceTypes/?spm=a2c63.p38356.879954.139.1eeb2d44eZQw2m#/instanceTypeByRegion) + +## Configuration +- Best practice is to configure credentials in the Environment variables - [Alicloud provider](https://registry.terraform.io/providers/aliyun/alicloud/latest/docs) +``` +Configure environment variables in Linux: + +$ export ALICLOUD_ACCESS_KEY=anaccesskey +$ export ALICLOUD_SECRET_KEY=asecretkey +$ export ALICLOUD_REGION=cn-beijing + +Configure envrionment variables in Windows: + set ALICLOUD_ACCESS_KEY=anaccesskey + set ALICLOUD_SECRET_KEY=asecretkey + set ALICLOUD_REGION=cn-beijing + +``` + +## Usage +- Fill all variables in the management/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + terraform init +- Create an execution plan: + terraform plan +- Create or modify the deployment: + terraform apply + +### terraform.tfvars variables: +| Name | Description | Type | Allowed values | Default | Required | +|-----------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|----------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| vswitch_id | Vswitch id | string | n/a | n/a | yes | +| instance_name | AliCloud instance name to launch | string | n/a | "CP-Management-tf" | no | +| instance_type | AliCloud instance type | string | - ecs.g6e.large
- ecs.g6e.xlarge
- ecs.g6e.2xlarge
- ecs.g6e.4xlarge
- ecs.g6e.8xlarge | "ecs.g6e.xlarge" | no | +| key_name | The ECS Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| eip | Allocate and associate an elastic IP with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) | number | n/a | 100 | no | +| disk_category | The ECS disk category | string | - cloud
- cloud_efficiency
- cloud_ssd,
- cloud_essd | "cloud_essd" | no | +| ram_role_name | RAM role name to attach to the instance profile, leave it empty for automatic creation | string | n/a | "" | no | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Management ECS Instance | map(string) | n/a | {} | no | +| version_license | Version and license of the Check Point Security Management | string | R81-BYOL | R81-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| password_hash | (Optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash) | string | n/a | "" | no | +| hostname | (Optional) Management prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | n/a | no | +| is_primary_management | Determines if this is the primary Management Server or not | bool | true/false | true | no | +| SICKey | "Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | n/a | true | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, SSH, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| primary_ntp | (Optional) | string | n/a | "ntp1.cloud.aliyuncs.com" | no | +| secondary_ntp | (Optional) | string | n/a | "ntp2.cloud.aliyuncs.com" | no | +| bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | + +## Example for terraform.tfvars + +``` +// --- VPC Network Configuration --- +vpc_id = "vpc-" +vswitch_id = "vsw-" + +// --- ECS Instances Configuration --- +instance_name = "CP-Management-tf" +instance_type = "ecs.g6e.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_essd" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +version_license = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +password_hash = "" +hostname = "mgmt-tf" + +// --- Security Management Server Settings --- +is_primary_management = "true" +SICKey = "" +allow_upload_download = "true" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" +``` + +## Outputs +| Name | Description | +|--------------------------|-------------------------------------------------| +| image_id | The ami id of the deployed Security Gateway | +| management_instance_id | The deployed Management AliCloud instance id | +| management_instance_name | The deployed Management AliCloud instance name | +| management_instance_tags | The deployed Management AliCloud tags | +| management_public_ip | The deployed Management AliCloud public address | + +## Revision History + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20230829 | Change default Check Point version to R81.20 | +| 20230615 | - Improved userdata quality and stability by moving to cloud-config
- Define default primary and secondary NTP servers
- Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230420 | Change alicloud terraform provider version to 1.203.0 | +| 20230330 | - Added support of ECS disk category.
- Stability fixes. | +| 20230129 | First release of R81.20 CloudGuard Management Terraform deployment in Alibaba Cloud. | | | | +| 20211011 | First release of Check Point CloudGaurd Management Terraform deployment into an existing VPC in Alibaba cloud. | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management/locals.tf b/deprecated/terraform/ali/R81/management/locals.tf new file mode 100755 index 00000000..b6815a6f --- /dev/null +++ b/deprecated/terraform/ali/R81/management/locals.tf @@ -0,0 +1,24 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // Will fail if var.gateway_management is invalid + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_cidr or var.gateway_addresses are invalid + mgmt_vswitch_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_cidr must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + version_split = element(split("-", var.version_license), 0) + gateway_bootstrap_script64 = base64encode(var.bootstrap_script) + gateway_SICkey_base64 = base64encode(var.SICKey) + gateway_password_hash_base64 = base64encode(var.password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management/main.tf b/deprecated/terraform/ali/R81/management/main.tf new file mode 100755 index 00000000..33b6d436 --- /dev/null +++ b/deprecated/terraform/ali/R81/management/main.tf @@ -0,0 +1,177 @@ +module "images" { + source = "../modules/images" + + version_license = var.version_license + chkp_type = "management" +} + +resource "alicloud_security_group" "management_sg" { + name = format("%s-SecurityGroup", var.instance_name) + description = "TF Management security group" + vpc_id = var.vpc_id +} + +resource "alicloud_security_group_rule" "permissive_egress" { + type = "egress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "-1/-1" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = "0.0.0.0/0" +} + +resource "alicloud_security_group_rule" "management_ingress-257" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "257/257" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.gateway_addresses +} + +resource "alicloud_security_group_rule" "management_ingress-8211" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "8211/8211" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.gateway_addresses +} + +resource "alicloud_security_group_rule" "management_ingress-18191-2" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "18191/18192" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.gateway_addresses +} + +resource "alicloud_security_group_rule" "management_ingress-18210-11" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "18210/18211" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.gateway_addresses +} + +resource "alicloud_security_group_rule" "management_ingress-18221" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "18221/18221" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.gateway_addresses +} + +resource "alicloud_security_group_rule" "management_ingress-18264" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "18264/18264" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.gateway_addresses +} + +resource "alicloud_security_group_rule" "management_ingress-22" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "22/22" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.admin_cidr +} + +resource "alicloud_security_group_rule" "management_ingress-433" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "433/433" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.admin_cidr +} + +resource "alicloud_security_group_rule" "management_ingress-18190" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "18190/18190" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.admin_cidr +} + +resource "alicloud_security_group_rule" "management_ingress-19009" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "19009/19009" + priority = 1 + security_group_id = alicloud_security_group.management_sg.id + cidr_ip = var.admin_cidr +} + +resource "alicloud_instance" "management_instance" { + instance_name = var.instance_name + instance_type = var.instance_type + key_name = var.key_name + image_id = module.images.image_id + vswitch_id = var.vswitch_id + security_groups = [alicloud_security_group.management_sg.id] + system_disk_size = var.volume_size + system_disk_category = var.disk_category + + tags = merge({ + Name = var.instance_name + }, var.instance_tags) + + user_data = templatefile("${path.module}/management_userdata.yaml", { + // script's arguments + Hostname = var.hostname, + PasswordHash = local.gateway_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + AdminSubnet = var.admin_cidr, + IsPrimary = var.is_primary_management, + SICKey = local.gateway_SICkey_base64, + AllocateElasticIP = var.allocate_and_associate_eip, + GatewayManagement = var.gateway_management, + BootstrapScript = local.gateway_bootstrap_script64, + OsVersion = local.version_split + }) +} + +module "common_eip" { + source = "../modules/common/elastic_ip" + allocate_and_associate_eip = var.allocate_and_associate_eip + instance_id = alicloud_instance.management_instance.id +} + +resource "alicloud_ram_role_attachment" "attach" { + count = var.ram_role_name != "" ? 1 : 0 + role_name = var.ram_role_name + instance_ids = alicloud_instance.management_instance.*.id +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management/management_userdata.yaml b/deprecated/terraform/ali/R81/management/management_userdata.yaml new file mode 100755 index 00000000..f65a203e --- /dev/null +++ b/deprecated/terraform/ali/R81/management/management_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py sicKey=\"${SICKey}\" installationType=\"management\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20230615\" templateName=\"management\" templateType=\"terraform\" shell=\"${Shell}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" primary=\"${IsPrimary}\" adminSubnet=\"${AdminSubnet}\" allocatePublicAddress=\"${AllocateElasticIP}\" "overTheInternet=\"${GatewayManagement}\"" bootstrapScript64=\"${BootstrapScript}\" diff --git a/deprecated/terraform/ali/R81/management/output.tf b/deprecated/terraform/ali/R81/management/output.tf new file mode 100755 index 00000000..82e2f5fe --- /dev/null +++ b/deprecated/terraform/ali/R81/management/output.tf @@ -0,0 +1,19 @@ +output "Deployment" { + value = "Finalizing configuration may take up to 20 minutes after deployment is finished" +} + +output "image_id" { + value = module.images.image_id +} +output "management_instance_id" { + value = alicloud_instance.management_instance.id +} +output "management_instance_name" { + value = alicloud_instance.management_instance.tags["Name"] +} +output "management_instance_tags" { + value = alicloud_instance.management_instance.tags +} +output "management_public_ip" { + value = module.common_eip.instance_eip_public_ip +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management/terraform.tfvars b/deprecated/terraform/ali/R81/management/terraform.tfvars new file mode 100755 index 00000000..9758387c --- /dev/null +++ b/deprecated/terraform/ali/R81/management/terraform.tfvars @@ -0,0 +1,35 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-" +vswitch_id = "vsw-" + +// --- ECS Instances Configuration --- +instance_name = "CP-Management-tf" +instance_type = "ecs.g6e.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +disk_category = "cloud_essd" +ram_role_name = "" +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +version_license = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +password_hash = "" +hostname = "mgmt-tf" + +// --- Security Management Server Settings --- +is_primary_management = "true" +SICKey = "" +allow_upload_download = "true" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "ntp1.cloud.aliyuncs.com" +secondary_ntp = "ntp2.cloud.aliyuncs.com" +bootstrap_script = "echo 'this is bootstrap script' > /home/admin/testfile.txt" \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management/variables.tf b/deprecated/terraform/ali/R81/management/variables.tf new file mode 100755 index 00000000..c91dd06e --- /dev/null +++ b/deprecated/terraform/ali/R81/management/variables.tf @@ -0,0 +1,128 @@ +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "vswitch_id" { + type = string + description = "To access the instance from the internet, make sure the vswitch has a route to the internet" +} + +// --- ECS Instance Configuration --- +variable "instance_name" { + type = string + description = "AliCloud instance name to launch" + default = "CP-Management-tf" +} +variable "instance_type" { + type = string + description = "" + default ="ecs.g6e.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.instance_type +} +variable "key_name" { + type = string + description = "The ECS Key Pair name to allow SSH access to the instances" +} +variable "allocate_and_associate_eip" { + type = bool + description = "When set to 'true', an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +variable "disk_category" { + type = string + description = "(Optional) Category of the ECS disk" + default = "cloud_essd" +} +variable "ram_role_name" { + type = string + description = "RAM role name to attach to the instance profile" + default = "" +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Management ECS Instance" +default = {} +} + +// --- Check Point Settings --- +variable "version_license" { + type = string + description = "version and license" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.version_license +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "hostname" { + type = string + description = "(Optional)" + default = "" +} + +// --- Security Management Server Settings --- +variable "is_primary_management" { + type = bool + description = "true/false. Determines if this is the primary management server or not" + default = true +} +variable "SICKey" { + type = string + description = "Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, SSH, and graphical clients only from this network to communicate with the Management Server" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Management Server" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "" +} +variable "bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/management/versions.tf b/deprecated/terraform/ali/R81/management/versions.tf new file mode 100755 index 00000000..71e9843e --- /dev/null +++ b/deprecated/terraform/ali/R81/management/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} diff --git a/deprecated/terraform/ali/R81/modules/cluster-ram-role/locals.tf b/deprecated/terraform/ali/R81/modules/cluster-ram-role/locals.tf new file mode 100755 index 00000000..395b7d40 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/cluster-ram-role/locals.tf @@ -0,0 +1,5 @@ +locals { + ram_role_name = format("%s-ram-role-%s", var.gateway_name, random_id.ram_uuid.hex) + ram_policy_name = format("%s-ram-policy-%s", var.gateway_name, random_id.ram_uuid.hex) + +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/cluster-ram-role/main.tf b/deprecated/terraform/ali/R81/modules/cluster-ram-role/main.tf new file mode 100755 index 00000000..95840d8b --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/cluster-ram-role/main.tf @@ -0,0 +1,54 @@ +resource "random_id" "ram_uuid" { + byte_length = 5 +} + +resource "alicloud_ram_role" "ram_role" { + name = local.ram_role_name + document = <= 100 ? 0 : "volume_size must be at least 100" +} +variable "disk_category" { + type = string + description = "(Optional) Category of the ECS disk" + default = "cloud_efficiency" +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateway" + default = "ecs.c5.xlarge" +} +module "validate_instance_type" { + source = "../instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway ECS Instance" + default = {} +} +variable "key_name" { + type = string + description = "The ECS Key Pair name to allow SSH access to the instance" +} +variable "image_id" { + type = string + description = "The image ID to use for the instance" +} +variable "security_groups" { + type = list(string) + description = "The security groups of the instance" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command \"openssl passwd -6 PASSWORD\" to get the PASSWORD's hash)" + default = "" +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional)" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/gateway_instance/versions.tf b/deprecated/terraform/ali/R81/modules/common/gateway_instance/versions.tf new file mode 100755 index 00000000..906a4df0 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/gateway_instance/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/instance_type/main.tf b/deprecated/terraform/ali/R81/modules/common/instance_type/main.tf new file mode 100755 index 00000000..4a3d6ba1 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/instance_type/main.tf @@ -0,0 +1,28 @@ +locals { + gw_types = [ + "ecs.g5ne.large", + "ecs.g5ne.xlarge", + "ecs.g5ne.2xlarge", + "ecs.g5ne.4xlarge", + "ecs.g5ne.8xlarge", + "ecs.g7ne.large", + "ecs.g7ne.xlarge", + "ecs.g7ne.2xlarge", + "ecs.g7ne.4xlarge", + "ecs.g7ne.8xlarge" + ] + mgmt_types = [ + "ecs.g6e.large", + "ecs.g6e.xlarge", + "ecs.g6e.2xlarge", + "ecs.g6e.4xlarge", + "ecs.g6e.8xlarge" + ] +} + +locals { + gw_values = var.chkp_type == "gateway" ? local.gw_types : [] + mgmt_values = var.chkp_type == "management" ? local.mgmt_types : [] + allowed_values = coalescelist(local.gw_values, local.mgmt_values) + is_allowed_type = index(local.allowed_values, var.instance_type) +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/instance_type/variables.tf b/deprecated/terraform/ali/R81/modules/common/instance_type/variables.tf new file mode 100755 index 00000000..f114cf20 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/instance_type/variables.tf @@ -0,0 +1,20 @@ +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +locals { + type_allowed_values = [ + "gateway", + "management" + //"server" + ] + // Will fail if var.chkp_type is invalid + validate_instance_type = index(local.type_allowed_values, var.chkp_type) +} + +variable "instance_type" { + type = string + description = "Alicloud Instance type" +} + diff --git a/deprecated/terraform/ali/R81/modules/common/instance_type/versions.tf b/deprecated/terraform/ali/R81/modules/common/instance_type/versions.tf new file mode 100755 index 00000000..0ec4dcca --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/instance_type/versions.tf @@ -0,0 +1,3 @@ +terraform { + required_version = ">= 0.14.3" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/internal_default_route/locals.tf b/deprecated/terraform/ali/R81/modules/common/internal_default_route/locals.tf new file mode 100755 index 00000000..493c4d9a --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/internal_default_route/locals.tf @@ -0,0 +1,3 @@ +locals { + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/internal_default_route/main.tf b/deprecated/terraform/ali/R81/modules/common/internal_default_route/main.tf new file mode 100755 index 00000000..7290ad9e --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/internal_default_route/main.tf @@ -0,0 +1,7 @@ +resource "alicloud_route_entry" "internal_default_route" { + count = local.internal_route_table_condition + route_table_id = var.private_route_table + destination_cidrblock = "0.0.0.0/0" + nexthop_type = "NetworkInterface" + nexthop_id = var.internal_eni_id +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/internal_default_route/output.tf b/deprecated/terraform/ali/R81/modules/common/internal_default_route/output.tf new file mode 100755 index 00000000..fde54050 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/internal_default_route/output.tf @@ -0,0 +1,3 @@ +output "internal_default_route_id" { + value = alicloud_route_entry.internal_default_route.*.id +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/internal_default_route/variables.tf b/deprecated/terraform/ali/R81/modules/common/internal_default_route/variables.tf new file mode 100755 index 00000000..b8e2f458 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/internal_default_route/variables.tf @@ -0,0 +1,9 @@ +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Gateway instance in the specified route table (e.g. rtb-12a34567)" + default="" +} +variable "internal_eni_id" { + type = string + description = "The internal-eni of the security gateway" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/internal_default_route/versions.tf b/deprecated/terraform/ali/R81/modules/common/internal_default_route/versions.tf new file mode 100755 index 00000000..906a4df0 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/internal_default_route/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/permissive_sg/main.tf b/deprecated/terraform/ali/R81/modules/common/permissive_sg/main.tf new file mode 100755 index 00000000..2ee7b17b --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/permissive_sg/main.tf @@ -0,0 +1,27 @@ +resource "alicloud_security_group" "permissive_sg" { + name = format("%s-PermissiveSecurityGroup", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) + description = "Permissive security group" + vpc_id = var.vpc_id +} + +resource "alicloud_security_group_rule" "permissive_egress" { + type = "egress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "-1/-1" + priority = 1 + security_group_id = alicloud_security_group.permissive_sg.id + cidr_ip = "0.0.0.0/0" +} + +resource "alicloud_security_group_rule" "permissive_ingress" { + type = "ingress" + ip_protocol = "all" + nic_type = "intranet" + policy = "accept" + port_range = "-1/-1" + priority = 1 + security_group_id = alicloud_security_group.permissive_sg.id + cidr_ip = "0.0.0.0/0" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/permissive_sg/output.tf b/deprecated/terraform/ali/R81/modules/common/permissive_sg/output.tf new file mode 100755 index 00000000..d8b5df1e --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/permissive_sg/output.tf @@ -0,0 +1,6 @@ +output "permissive_sg_id" { + value = alicloud_security_group.permissive_sg.id +} +output "permissive_sg_name" { + value = alicloud_security_group.permissive_sg.name +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/permissive_sg/variables.tf b/deprecated/terraform/ali/R81/modules/common/permissive_sg/variables.tf new file mode 100755 index 00000000..d2afaad2 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/permissive_sg/variables.tf @@ -0,0 +1,13 @@ +variable "vpc_id" { + type = string +} +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway-tf" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/permissive_sg/versions.tf b/deprecated/terraform/ali/R81/modules/common/permissive_sg/versions.tf new file mode 100755 index 00000000..906a4df0 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/permissive_sg/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/version_license/main.tf b/deprecated/terraform/ali/R81/modules/common/version_license/main.tf new file mode 100755 index 00000000..94d144cd --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/version_license/main.tf @@ -0,0 +1,23 @@ +locals { + gw_versions = [ + //"R81-PAYG-NGTP", + // "R81-PAYG-NGTX", + "R81-BYOL", + "R81.10-BYOL", + "R81.20-BYOL" + ] + mgmt_versions = [ + //"R81-PAYG", + "R81-BYOL", + "R81.10-BYOL", + "R81.20-BYOL" + ] +} + +locals { + gw_values = var.chkp_type == "gateway" ? local.gw_versions : [] + mgmt_values = var.chkp_type == "management" ? local.mgmt_versions : [] + // standalone_values = var.chkp_type == "standalone" ? local.standalone_versions : [] + allowed_values = coalescelist(local.gw_values, local.mgmt_values)//, local.standalone_values) + is_allowed_type = index(local.allowed_values, var.version_license) +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/common/version_license/variables.tf b/deprecated/terraform/ali/R81/modules/common/version_license/variables.tf new file mode 100755 index 00000000..9ecf1643 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/version_license/variables.tf @@ -0,0 +1,19 @@ +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +locals { + type_allowed_values = [ + "gateway", + "management", + "standalone",] + // Will fail if var.chkp_type is invalid + validate_chkp_type = index(local.type_allowed_values, var.chkp_type) +} + +variable "version_license" { + type = string + description = "AliCloud Version license" +} + diff --git a/deprecated/terraform/ali/R81/modules/common/version_license/versions.tf b/deprecated/terraform/ali/R81/modules/common/version_license/versions.tf new file mode 100755 index 00000000..906a4df0 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/common/version_license/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/images/images.yaml b/deprecated/terraform/ali/R81/modules/images/images.yaml new file mode 100755 index 00000000..c2eb1d52 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/images/images.yaml @@ -0,0 +1,210 @@ +Description: Returns a Check Point AliCloud Machine ID (__VERSION__) +Parameters: + Version: + Description: Security Gateway or Management Server version + Type: String + Default: R81.20-BYOL-GW + AllowedValues: + - R81-BYOL-GW + - R81-BYOL-MGMT + - R81.10-BYOL-GW + - R81.10-BYOL-MGMT + - R81.20-BYOL-GW + - R81.20-BYOL-MGMT +Mappings: + ConverterMap: + R81-BYOL-GW: + Value: R81BYOLGW + R81-BYOL-MGMT: + Value: R81BYOLMGMT + R81.10-BYOL-GW: + Value: R8110BYOLGW + R81.10-BYOL-MGMT: + Value: R8110BYOLMGMT + R81.20-BYOL-GW: + Value: R8120BYOLGW + R81.20-BYOL-MGMT: + Value: R8120BYOLMGMT + RegionMap: + cn-hongkong: + R81BYOLMGMT: m-j6c55b1lpz95colzzz1y + R81BYOLGW: m-j6c3gd3gcahojs40842v + R8110BYOLMGMT: m-j6c5n6p0tkx8clx72qes + R8110BYOLGW: m-j6c0x6ugw2012axbdmkn + R8120BYOLMGMT: m-j6c2gv0tohwb5otjzbk4 + R8120BYOLGW: m-j6cdnsm44k0csckg4cxa + ap-southeast-1: + R81BYOLMGMT: m-t4ngdphpnhzw065e30jt + R81BYOLGW: m-t4n99ag8zbinnc7n7xmw + R8110BYOLMGMT: m-t4n9x963l2fx13d4mzi8 + R8110BYOLGW: m-t4ndsvficp1ukrcpt4as + R8120BYOLMGMT: m-t4n3m9t1icbv1ptf8b67 + R8120BYOLGW: m-t4nj16t8nnlp7a70214i + us-west-1: + R81BYOLMGMT: m-rj95ffd9q3c8u7rpc7v5 + R81BYOLGW: m-rj9eblv5oe0ypm77no86 + R8110BYOLMGMT: m-rj9ebcmy6gxp3lzkjnrp + R8110BYOLGW: m-rj952h5pzgaecqhg9h6u + R8120BYOLMGMT: m-rj92n7t0j5uvmss2dak5 + R8120BYOLGW: m-rj99hmyezcyqa0in2us9 + us-east-1: + R81BYOLMGMT: m-0xi064illsngi8q7ejln + R81BYOLGW: m-0xiiv7m3m3ex8zai0lq4 + R8110BYOLMGMT: m-0xie3j6n8rxa26v6abni + R8110BYOLGW: m-0xiebcmy6gxpiyg830vh + R8120BYOLMGMT: m-0xihsclzmkgsxpsmfil2 + R8120BYOLGW: m-0xickak3e8yimpt90lh9 + ap-southeast-2: + R81BYOLMGMT: m-p0w0pl2rajygi6otl2mh + R81BYOLGW: m-p0w78ynl3rpgo1yq43qf + R8110BYOLMGMT: m-p0w7z34zl8gl2nmgzo75 + R8110BYOLGW: m-p0w2nhgtaqxil6bruwe2 + R8120BYOLMGMT: m-p0w2mgbmrn1pq4973ncq + R8120BYOLGW: m-p0wd45q8v82grbipwqkw + ap-southeast-3: + R81BYOLMGMT: m-8psi42zrfpq57cibgu2b + R81BYOLGW: m-8ps8swns48itw97zsb2i + R8110BYOLMGMT: m-8psc710cdd9x9guiajuk + R8110BYOLGW: m-8ps6mel7llq3ffzc2txa + R8120BYOLMGMT: m-8psc710cdd9x6k9vbn5m + R8120BYOLGW: m-8psf1zkz08byz41qrt1r + ap-southeast-5: + R81BYOLMGMT: m-k1aajdkea2t5oyxicbu8 + R81BYOLGW: m-k1afqua8zzbgdaosx7sf + R8110BYOLMGMT: m-k1ahug645c79svl6tgbp + R8110BYOLGW: m-k1a6n0hj1qidjiig80o0 + R8120BYOLMGMT: m-k1ahgt585wlm71lmpmg1 + R8120BYOLGW: m-k1a20f2u7nspfcja9mfc + ap-southeast-6: + R81BYOLMGMT: m-5ts832hgbk52wwnxzjlx + R81BYOLGW: m-5tsf5buudxrwbijypr0v + R8110BYOLMGMT: m-5tsa5qwchhf7q22qj685 + R8110BYOLGW: m-5tsdw01mce246abvrnes + R8120BYOLMGMT: m-5ts5ukwjgsl6t34hx7po + R8120BYOLGW: m-5tsa5qwchhf7pw5n70as + ap-northeast-1: + R81BYOLMGMT: m-6we8l9kvu9shqf3j5v4e + R81BYOLGW: m-6we42rtltap69nckfynw + R8110BYOLMGMT: m-6we20qh4jffzabapyyle + R8110BYOLGW: m-6wefezctjbied9npzp1n + R8120BYOLMGMT: m-6weihbzpoyt5h6i2i42e + R8120BYOLGW: m-6we215381e51fkneyv5v + eu-central-1: + R81BYOLMGMT: m-gw81j322yjmx03hq26qt + R81BYOLGW: m-gw82fm7sbwj7x6fpj1mn + R8110BYOLMGMT: m-gw89gvg18gk6nzo3gxe1 + R8110BYOLGW: m-gw8divjg7azjl2ndt34v + R8120BYOLMGMT: m-gw8csbodb1ntgbtu653c + R8120BYOLGW: m-gw83wxmsb5524ke9f6m7 + eu-west-1: + R81BYOLMGMT: m-d7ocob57ud2nqiv9fk8w + R81BYOLGW: m-d7oez9xgn0qg5g815tip + R8110BYOLMGMT: m-d7o7nj4f81gs8cyo52jd + R8110BYOLGW: m-d7o7nj4f81gsnpfbofnh + R8120BYOLMGMT: m-d7o63e77fokjsv4aq4kt + R8120BYOLGW: m-d7oj29ec4xx04sr8h61z + me-east-1: + R81BYOLMGMT: m-eb35op3wyu89kabry2zw + R81BYOLGW: m-eb35op3wyu89iv0z0nmz + R8110BYOLMGMT: m-eb33tyrfiy726a0xlw6g + R8110BYOLGW: m-eb30m4ho9mkzfb3xi78i + R8120BYOLMGMT: m-eb3bbb1nen46tqmcujmn + R8120BYOLGW: m-eb3dphy5uzm33cduxr7i + ap-south-1: + R81BYOLMGMT: m-a2d16a0v0ms9mg5xh1nm + R81BYOLGW: m-a2didx39bhgf547thni0 + R8110BYOLMGMT: m-a2d4ffz0q8dflg62j0zq + R8110BYOLGW: m-a2d9j14yemliag92m9d1 + R8120BYOLMGMT: m-a2d1e5s7uy9vv5a6n9cn + R8120BYOLGW: m-a2d1e5s7uy9vxvxqa04e + ap-southeast-7: + R81BYOLMGMT: m-0jo742iyh0qbzg51b6fd + R81BYOLGW: m-0joian1mgt9qt2lpvfnk + R8110BYOLMGMT: m-0jo3qwrwsdx3663is0b4 + R8110BYOLGW: m-0jogq1yzljp8ziw4caci + R8120BYOLMGMT: m-0jo67k42jvg301wis5ol + R8120BYOLGW: m-0jo5t1ypg4zy4h12i9c5 + ap-northeast-2: + R81BYOLMGMT: m-mj75cxsn1dhdiqhfc3a0 + R81BYOLGW: m-mj7bybnr5b9gebqrf3xt + R8110BYOLMGMT: m-mj7h0j7db1ryrwczg9ef + R8110BYOLGW: m-mj73osasl4gyi0zqscr5 + R8120BYOLMGMT: m-mj7aktw6610pznjgb16z + R8120BYOLGW: m-mj79jylrqomj0fv99s3b + cn-qingdao: + R81BYOLMGMT: m-m5e1i33z6ohq98tllukn + R81BYOLGW: m-m5eb1zyo5cjbvte7ovay + R8110BYOLMGMT: m-m5eftm32pjq4ghtwcn25 + R8110BYOLGW: m-m5ef0hxxec3ws2c2y26b + R8120BYOLMGMT: m-m5ebt96quorb2gj7dhku + R8120BYOLGW: m-m5eftm32pjq4g9xrwf5o + cn-beijing: + R81BYOLMGMT: m-2ze5d2jit72gotjw5d77 + R81BYOLGW: m-2zec8i2qli4cnqfw9e3o + R8110BYOLMGMT: m-2zehvbpbae19t51owc0j + R8110BYOLGW: m-2zeiwvllkl9jybavtmey + R8120BYOLMGMT: m-2ze1781062lxfwe35d1p + R8120BYOLGW: m-2ze347cq3f6fg3udyb1p + cn-zhangjiakou: + R81BYOLMGMT: m-8vb1rjkshxdaynvqbexj + R81BYOLGW: m-8vb1rjkshxdax8kxdzkk + R8110BYOLMGMT: m-8vb83tbc4hwpesbvte9d + R8110BYOLGW: m-8vbblzj10mzvpnkzdint + R8120BYOLMGMT: m-8vbeoj3rrq2tm6o5bhaa + R8120BYOLGW: m-8vbd1bffbjhlxjkb0k4i + cn-huhehaote: + R81BYOLMGMT: m-hp309790we62uhpo5eed + R81BYOLGW: m-hp3ab2tvfxuar5snxu2r + R8110BYOLMGMT: m-hp3h3tzxij7kl9tdrqg2 + R8110BYOLGW: m-hp325dwey9rn4tyiyuyu + R8120BYOLMGMT: m-hp31ci7e1eeaj062wki0 + R8120BYOLGW: m-hp31ci7e1eealqtmjb9n + cn-wulanchabu: + R81BYOLMGMT: m-0jlhwuucdujv3wee7m96 + R81BYOLGW: m-0jle5qxpr97s1c64e72k + R8110BYOLMGMT: m-0jl54w11sr4odheytky1 + R8110BYOLGW: m-0jlbavg2r5fjc4jxypp7 + R8120BYOLMGMT: m-0jl54w11sr4oakubuo94 + R8120BYOLGW: m-0jlbavg2r5fiwm6736o3 + cn-hangzhou: + R81BYOLMGMT: m-bp14kps2wrk6qquv5ok0 + R81BYOLGW: m-bp1aa9u6zcazi4o1hnjh + R8110BYOLMGMT: m-bp1dz2nq9fqppcf8smpk + R8110BYOLGW: m-bp1hamqhfny1smyl8ql7 + R8120BYOLMGMT: m-bp149dep83kgo5p0dw3l + R8120BYOLGW: m-bp1gvq0d0413vbnakoqj + cn-shanghai: + R81BYOLMGMT: m-uf6cj9tqmxx1bsfmbu45 + R81BYOLGW: m-uf63qkdigbprn96zy3vm + R8110BYOLMGMT: m-uf655j7a9r7otwa2xemv + R8110BYOLGW: m-uf6idj2b3zt57omxvzbr + R8120BYOLMGMT: m-uf62vrhc5bapfoy9lw7n + R8120BYOLGW: m-uf6c9vxp1n58y56ep033 + cn-shenzhen: + R81BYOLMGMT: m-wz9d9s75jsh11z089uuj + R81BYOLGW: m-wz9czejz43gyhdztsjnr + R8110BYOLMGMT: m-wz95gswem9lea2z0d9se + R8110BYOLGW: m-wz93e5pwshkmiv35y9ii + R8120BYOLMGMT: m-wz9am290ax9js6dfdt5o + R8120BYOLGW: m-wz94fs2enyvm6qhx3ged + cn-heyuan: + R81BYOLMGMT: m-f8z61z784gwfm1fhxgre + R81BYOLGW: m-f8z7wvp6hhvsvevtpb0j + R8110BYOLMGMT: m-f8z5o7741si10yq0piws + R8110BYOLGW: m-f8z985hmyc9d8951pr76 + R8120BYOLMGMT: m-f8zj0s3cyg3glnlz414g + R8120BYOLGW: m-f8z5o7741si10ssxdczf + cn-guangzhou: + R81BYOLMGMT: m-7xv95xjo0yd0lg4y1z9p + R81BYOLGW: m-7xv95xjo0yd0k0u54jwr + R8110BYOLMGMT: m-7xv4bih29ge5i2je9amd + R8110BYOLGW: m-7xv7i7fhzogppdgxa2cc + R8120BYOLMGMT: m-7xv3lyr4gpzmp8ei0qgi + R8120BYOLGW: m-7xv7i7fhzogp9v36ejbr + cn-chengdu: + R81BYOLMGMT: m-2vcho1h20xnncjlroavq + R81BYOLGW: m-2vc0m9vq9oty74yz83d4 + R8110BYOLMGMT: m-2vc13w2rjk7p9o285gtj + R8110BYOLGW: m-2vc13w2rjk7pp0ivotxs + R8120BYOLMGMT: m-2vc0nlbyccv29t5ql0oh + R8120BYOLGW: m-2vcd6ume44qej9ffhaxg diff --git a/deprecated/terraform/ali/R81/modules/images/main.tf b/deprecated/terraform/ali/R81/modules/images/main.tf new file mode 100755 index 00000000..86231617 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/images/main.tf @@ -0,0 +1,20 @@ +locals { + images_yaml_regionMap = yamldecode(split("Resources", file("${path.module}/images.yaml"))[0]).Mappings.RegionMap + images_yaml_converterMap = yamldecode(split("Resources", file("${path.module}/images.yaml"))[0]).Mappings.ConverterMap + + + // Variables example: + // version_license = "R81.20-BYOL" + // RESULT: + // version_license_key = "R81.20-BYOL-GW" + // version_license_value = "R8120BYOLGW" + + version_license_key = format("%s%s", var.version_license, var.chkp_type == "gateway" ? "-GW" : var.chkp_type == "management" ? "-MGMT" : "") + version_license_value = local.images_yaml_converterMap[local.version_license_key]["Value"] + + // Variables example: + // region = "us-east-1" + // version_license_key - see above + // RESULT: local.image_id = "m-1234567" + image_id = local.images_yaml_regionMap[local.region][local.version_license_value] +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/images/output.tf b/deprecated/terraform/ali/R81/modules/images/output.tf new file mode 100755 index 00000000..a4611551 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/images/output.tf @@ -0,0 +1,6 @@ +output "image_id" { + value = local.image_id +} +output "version_license_with_sufix" { + value = local.version_license_key +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/images/variables.tf b/deprecated/terraform/ali/R81/modules/images/variables.tf new file mode 100755 index 00000000..0c646605 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/images/variables.tf @@ -0,0 +1,20 @@ +data "alicloud_regions" "current" { + current = true +} +locals { + region = data.alicloud_regions.current.regions.0.id +} + +// --- Version and license --- +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} + +variable "version_license" { + type = string + description = "Version and license" + default = "R81.20-BYOL" +} + diff --git a/deprecated/terraform/ali/R81/modules/images/versions.tf b/deprecated/terraform/ali/R81/modules/images/versions.tf new file mode 100755 index 00000000..0ec4dcca --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/images/versions.tf @@ -0,0 +1,3 @@ +terraform { + required_version = ">= 0.14.3" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/vpc/locals.tf b/deprecated/terraform/ali/R81/modules/vpc/locals.tf new file mode 100755 index 00000000..1e3622f2 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/vpc/locals.tf @@ -0,0 +1,6 @@ +locals { + regex_valid_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" +} \ No newline at end of file diff --git a/deprecated/terraform/ali/R81/modules/vpc/main.tf b/deprecated/terraform/ali/R81/modules/vpc/main.tf new file mode 100755 index 00000000..55ae14a9 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/vpc/main.tf @@ -0,0 +1,38 @@ +// --- VPC --- +resource "alicloud_vpc" "vpc" { + cidr_block = var.vpc_cidr + vpc_name = var.vpc_name +} + +// --- Public Vswitch --- +resource "alicloud_vswitch" "publicVsw" { + for_each = var.public_vswitchs_map + + vpc_id = alicloud_vpc.vpc.id + zone_id = each.key + cidr_block = cidrsubnet(alicloud_vpc.vpc.cidr_block, var.vswitchs_bit_length, each.value) + vswitch_name = format("Public-vswitch-%s", each.value) + tags = {} +} + +// --- Management Vswitch --- +resource "alicloud_vswitch" "managementVsw" { + for_each = var.management_vswitchs_map + + vpc_id = alicloud_vpc.vpc.id + zone_id = each.key + cidr_block = cidrsubnet(alicloud_vpc.vpc.cidr_block, var.vswitchs_bit_length, each.value) + vswitch_name = format("Management-vswitch-%s", each.value) + tags = {} +} + +// --- Private Vswitch --- +resource "alicloud_vswitch" "privateVsw" { + for_each = var.private_vswitchs_map + + vpc_id = alicloud_vpc.vpc.id + zone_id = each.key + cidr_block = cidrsubnet(alicloud_vpc.vpc.cidr_block, var.vswitchs_bit_length, each.value) + vswitch_name = format("Private-vswitch-%s", each.value) + tags = {} +} diff --git a/deprecated/terraform/ali/R81/modules/vpc/output.tf b/deprecated/terraform/ali/R81/modules/vpc/output.tf new file mode 100755 index 00000000..ce218660 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/vpc/output.tf @@ -0,0 +1,15 @@ +output "vpc_id" { + value = alicloud_vpc.vpc.id +} +output "vpc_name" { + value = alicloud_vpc.vpc.name +} +output "public_vswitchs_ids_list" { + value = [for public_vswitch in alicloud_vswitch.publicVsw : public_vswitch.id ] +} +output "management_vswitchs_ids_list" { + value = [for management_vswitch in alicloud_vswitch.managementVsw : management_vswitch.id ] +} +output "private_vswitchs_ids_list" { + value = [for private_vswitch in alicloud_vswitch.privateVsw : private_vswitch.id] +} diff --git a/deprecated/terraform/ali/R81/modules/vpc/variables.tf b/deprecated/terraform/ali/R81/modules/vpc/variables.tf new file mode 100755 index 00000000..bb0807f5 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/vpc/variables.tf @@ -0,0 +1,23 @@ +variable "vpc_cidr" { + type = string +} +variable "vpc_name" { + type = string +} +variable "public_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"cn-hangzhou-e\" = 1} ) " +} +variable "management_vswitchs_map" { + type = map(string) + description = "(Optional) A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"cn-hangzhou-e\" = 3} ) " + default = {} +} +variable "private_vswitchs_map" { + type = map(string) + description = "A map of pairs {availability-zone = vswitch-suffix-number}. Each entry creates a vswitch. Minimum 1 pair. (e.g. {\"cn-hangzhou-f\" = 3} ) " +} +variable "vswitchs_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a vswitchs_bit_length value is 4, the resulting vswitch address will have length /20" +} diff --git a/deprecated/terraform/ali/R81/modules/vpc/versions.tf b/deprecated/terraform/ali/R81/modules/vpc/versions.tf new file mode 100755 index 00000000..906a4df0 --- /dev/null +++ b/deprecated/terraform/ali/R81/modules/vpc/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + alicloud = { + source = "hashicorp/alicloud" + version = "1.203.0" + } + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/README.md b/deprecated/terraform/aws/R80.40/autoscale-gwlb/README.md new file mode 100755 index 00000000..0e04c944 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/README.md @@ -0,0 +1,185 @@ +# Check Point CloudGuard Network Auto Scaling GWLB Terraform module for AWS + +Terraform module which deploys an Auto Scaling Group of Check Point Security Gateways into an existing VPC. + +These types of Terraform resources are supported: +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [Security group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) + + +See the [CloudGuard Auto Scaling for AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CloudGuard_Network_for_AWS_AutoScaling_DeploymentGuide/Topics-AWS-AutoScale-DG/Check-Point-CloudGuard-Network-for-AWS.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/autoscale/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "env1" + asg_name = "autoscaling_group" + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_ids = ["subnet-abc123", "subnet-def456"] + + // --- Automatic Provisioning with Security Management Server Settings --- + gateways_provision_address_type = "private" + allocate_public_IP = false + management_server = "mgmt_env1" + configuration_template = "tmpl_env1" + + // --- EC2 Instances Configuration --- + gateway_name = "asg_gateway" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + instances_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Auto Scaling Configuration --- + minimum_group_size = 2 + maximum_group_size = 10 + target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_instance_connect = false + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission +- To tear down your resources: + ``` + terraform destroy + ``` + + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|----------------------------|----------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_ids | List of public subnet IDs to launch resources into. Recommended at least 2 | list(string) | n/a | n/a | yes | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_server | The name that represents the Security Management Server in the CME configuration | string | n/a | n/a | yes | +| configuration_template | Name of the provisioning template in the CME configuration | string | n/a | n/a | yes | +| gateway_name | The name tag of the Security Gateways instances | string | n/a | Check-Point-ASG-gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| instances_tags | (Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances | map(string) | n/a | {} | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| minimum_group_size | The minimum number of instances in the Auto Scaling group | number | n/a | 2 | no | +| maximum_group_size | The maximum number of instances in the Auto Scaling group | number | n/a | 10 | no | +| target_groups | (Optional) List of Target Group ARNs to associate with the Auto Scaling group | list(string) | n/a | [] | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters) | string | n/a | "12345678" | yes | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|------------------------------------------------|-------------------------------------------------------------------| +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_autoscaling_group_availability_zones | The AZs on which the Autoscaling Group is configured | +| autoscale_autoscaling_group_desired_capacity | The deployed AutoScaling Group's desired capacity of instances | +| autoscale_autoscaling_group_min_size | The deployed AutoScaling Group's minimum number of instances | +| autoscale_autoscaling_group_max_size | The deployed AutoScaling Group's maximum number of instances | +| autoscale_autoscaling_group_target_group_arns | The deployed AutoScaling Group's configured target groups | +| autoscale_autoscaling_group_subnets | The subnets on which the deployed AutoScaling Group is configured | +| autoscale_launch_template_id | The id of the Launch Template | +| autoscale_autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240417 | - Add support for Elastic Load Balancer Health Checks.
- EC2 Auto Scaling will start to detect and act on health checks performed by Elastic Load Balancing. | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point Auto Scaling GWLB Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/asg_userdata.yaml b/deprecated/terraform/aws/R80.40/autoscale-gwlb/asg_userdata.yaml new file mode 100755 index 00000000..bb095c01 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/asg_userdata.yaml @@ -0,0 +1,29 @@ +#cloud-config +network: + version: 1 + config: + - type: bridge + name: br0 + mtu: *eth0-mtu + subnets: + - address: *eth0-private + type: static + gateway: *default-gateway + dns_nameservers: + - *eth0-dns1 + bridge_interfaces: + - eth0 +kernel_parameters: + sim: + - sim_geneve_enabled=1 + - sim_geneve_br_dev=br0 + fw: + + - fwtls_bridge_mode_inspection=1 + - fw_geneve_enabled=1 +bootcmd: + - echo "brctl hairpin br0 eth0 on" >> /etc/rc.local + - echo "cpprod_util CPPROD_SetValue \"fw1\" \"AwsGwlb\" 4 1 1" >> /etc/rc.local +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" installationType=\"autoscale\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"autoscale_gwlb\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" bootstrapScript64=\"${BootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/locals.tf b/deprecated/terraform/aws/R80.40/autoscale-gwlb/locals.tf new file mode 100755 index 00000000..ef1abdf2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/locals.tf @@ -0,0 +1,56 @@ +locals { + asg_name = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.asg_name) + create_iam_role = var.enable_cloudwatch ? 1 : 0 + + gateways_provision_address_type_allowed_values = [ + "public", + "private" + ] + // Will fail if var.gateways_provision_address_type is invalid + validate_gateways_provision_address_type = index(local.gateways_provision_address_type_allowed_values, var.gateways_provision_address_type) + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh" + ] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SICKey] must be at least 8 alphanumeric characters" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + + tags_asg_format = null_resource.tags_as_list_of_maps.*.triggers + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) + gateway_password_hash_base64 = base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) + is_gwlb_ami = length(regexall(".*R80.40.*", var.gateway_version)) > 0 + +} +resource "null_resource" "tags_as_list_of_maps" { + count = length(keys(var.instances_tags)) + + triggers = { + "key" = keys(var.instances_tags)[count.index] + "value" = values(var.instances_tags)[count.index] + "propagate_at_launch" = "true" + } +} diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/main.tf b/deprecated/terraform/aws/R80.40/autoscale-gwlb/main.tf new file mode 100755 index 00000000..6a43b892 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/main.tf @@ -0,0 +1,202 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + version_license = var.gateway_version + amis_url = local.is_gwlb_ami == true ? "https://cgi-cfts-staging.s3.amazonaws.com/gwlb/amis-gwlb.yaml" : "https://cgi-cfts-staging.s3.amazonaws.com/utils/amis.yaml" + +} + +resource "aws_security_group" "permissive_sg" { + name_prefix = format("%s_PermissiveSecurityGroup", local.asg_name) + description = "Permissive security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + tags = { + Name = format("%s_PermissiveSecurityGroup", local.asg_name) + } +} + +resource "aws_launch_template" "asg_launch_template" { + name_prefix = local.asg_name + image_id = module.amis.ami_id + instance_type = var.gateway_instance_type + key_name = var.key_name + network_interfaces { + associate_public_ip_address = var.allocate_public_IP + security_groups = [aws_security_group.permissive_sg.id] + } + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + iam_instance_profile { + name = ( var.enable_cloudwatch ? aws_iam_instance_profile.instance_profile[0].name : "") + } + + monitoring { + enabled = true + } + + block_device_mappings { + device_name = "/dev/xvda" + ebs { + volume_type = var.volume_type + volume_size = var.volume_size + encrypted = var.enable_volume_encryption + } + } + + description = "Initial template version" + + user_data = base64encode(templatefile("${path.module}/asg_userdata.yaml", { + // script's arguments + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + EnableCloudWatch = var.enable_cloudwatch, + EnableInstanceConnect = var.enable_instance_connect, + Shell = var.admin_shell, + SICKey = local.gateway_SICkey_base64, + AllowUploadDownload = var.allow_upload_download, + BootstrapScript = local.gateway_bootstrap_script64, + OsVersion = local.version_split + })) +} +resource "aws_autoscaling_group" "asg" { + name_prefix = local.asg_name + launch_template { + id = aws_launch_template.asg_launch_template.id + version = aws_launch_template.asg_launch_template.latest_version + } + min_size = var.minimum_group_size + max_size = var.maximum_group_size + target_group_arns = var.target_groups + vpc_zone_identifier = var.subnet_ids + health_check_grace_period = 3600 + health_check_type = "ELB" + + tag { + key = "Name" + value = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.gateway_name) + propagate_at_launch = true + } + + tag { + key = "x-chkp-tags" + value = format("management=%s:template=%s:ip-address=%s", var.management_server, var.configuration_template, var.gateways_provision_address_type) + propagate_at_launch = true + } + + tag { + key = "x-chkp-topology" + value = "internal" + propagate_at_launch = true + } + + tag { + key = "x-chkp-solution" + value = "autoscale_gwlb" + propagate_at_launch = true + } + + dynamic "tag" { + for_each = var.instances_tags + content { + key = tag.key + value = tag.value + propagate_at_launch = true + } + } +} + +data "aws_iam_policy_document" "assume_role_policy_document" { + version = "2012-10-17" + statement { + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + effect = "Allow" + } +} + +resource "aws_iam_role" "role" { + count = local.create_iam_role + name_prefix = format("%s-iam_role", local.asg_name) + assume_role_policy = data.aws_iam_policy_document.assume_role_policy_document.json + path = "/" +} +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.create_iam_role + role = aws_iam_role.role[count.index].name + tag_name = local.asg_name +} +resource "aws_iam_instance_profile" "instance_profile" { + count = local.create_iam_role + name_prefix = format("%s-iam_instance_profile", local.asg_name) + path = "/" + role = aws_iam_role.role[count.index].name +} + +// Scaling metrics +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_low" { + alarm_name = format("%s_alarm_low", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-down if CPU < 60% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 60 + alarm_actions = [aws_autoscaling_policy.scale_down_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "LessThanThreshold" +} +resource "aws_autoscaling_policy" "scale_down_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_down", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = -1 +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_high" { + alarm_name = format("%s_alarm_high", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-up if CPU > 80% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 80 + alarm_actions = [aws_autoscaling_policy.scale_up_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "GreaterThanThreshold" +} +resource "aws_autoscaling_policy" "scale_up_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_up", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = 1 +} diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/output.tf b/deprecated/terraform/aws/R80.40/autoscale-gwlb/output.tf new file mode 100755 index 00000000..ce5f76ce --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/output.tf @@ -0,0 +1,41 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} + +output "autoscale_autoscaling_group_name" { + value = aws_autoscaling_group.asg.name +} +output "autoscale_autoscaling_group_arn" { + value = aws_autoscaling_group.asg.arn +} +output "autoscale_autoscaling_group_availability_zones" { + value = aws_autoscaling_group.asg.availability_zones +} +output "autoscale_autoscaling_group_desired_capacity" { + value = aws_autoscaling_group.asg.desired_capacity +} +output "autoscale_autoscaling_group_min_size" { + value = aws_autoscaling_group.asg.min_size +} +output "autoscale_autoscaling_group_max_size" { + value = aws_autoscaling_group.asg.max_size +} +output "autoscale_autoscaling_group_target_group_arns" { + value = aws_autoscaling_group.asg.target_group_arns +} +output "autoscale_autoscaling_group_subnets" { + value = aws_autoscaling_group.asg.vpc_zone_identifier +} + +output "autoscale_launch_template_id" { + value = aws_launch_template.asg_launch_template.id +} + +output "autoscale_security_group_id" { + value = aws_security_group.permissive_sg.id +} + +output "autoscale_iam_role_name" { + value = aws_iam_role.role.*.name +} + diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/terraform.tfvars b/deprecated/terraform/aws/R80.40/autoscale-gwlb/terraform.tfvars new file mode 100755 index 00000000..4cced958 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/terraform.tfvars @@ -0,0 +1,42 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "env1" +asg_name = "autoscaling_group" + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_ids = ["subnet-abc123", "subnet-def456"] + +// --- Automatic Provisioning with Security Management Server Settings --- +gateways_provision_address_type = "private" +allocate_public_IP = false +management_server = "mgmt_env1" +configuration_template = "tmpl_env1" + +// --- EC2 Instances Configuration --- +gateway_name = "asg_gateway" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +instances_tags = { + key1 = "value1" + key2 = "value2" +} +metadata_imdsv2_required = true + +// --- Auto Scaling Configuration --- +minimum_group_size = 2 +maximum_group_size = 10 +target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_instance_connect = false +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/variables.tf b/deprecated/terraform/aws/R80.40/autoscale-gwlb/variables.tf new file mode 100755 index 00000000..cb1a985c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/variables.tf @@ -0,0 +1,191 @@ +// Module: Check Point CloudGuard Network Auto Scaling Group into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. Recommended at least 2" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the CME configuration" +} +variable "configuration_template" { + type = string + description = "Name of the provisioning template in the CME configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} + +// --- EC2 Instances Configuration --- +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateways instances" + default = "Check-Point-ASG-gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "instances_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances" + default = {} +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} + +// --- Auto Scaling Configuration --- +variable "minimum_group_size" { + type = number + description = "The minimum number of instances in the Auto Scaling group" + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximum number of instances in the Auto Scaling group" + default = 10 +} +variable "target_groups" { + type = list(string) + description = "(Optional) List of Target Group ARNs to associate with the Auto Scaling group" + default = [] +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} + +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/autoscale-gwlb/versions.tf b/deprecated/terraform/aws/R80.40/autoscale-gwlb/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale-gwlb/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/autoscale/README.md b/deprecated/terraform/aws/R80.40/autoscale/README.md new file mode 100755 index 00000000..44bf6125 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/README.md @@ -0,0 +1,199 @@ +# Check Point CloudGuard Network Auto Scaling Terraform module for AWS + +Terraform module which deploys an Auto Scaling Group of Check Point Security Gateways into an existing VPC. + +These types of Terraform resources are supported: +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation +* [Proxy Elastic Load Balancer](https://www.terraform.io/docs/providers/aws/r/elb.html) - conditional creation + + +See the [CloudGuard Auto Scaling for AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CloudGuard_Network_for_AWS_AutoScaling_DeploymentGuide/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/autoscale/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "env1" + asg_name = "autoscaling_group" + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_ids = ["subnet-abc123", "subnet-def456"] + + // --- Automatic Provisioning with Security Management Server Settings --- + gateways_provision_address_type = "private" + management_server = "mgmt_env1" + configuration_template = "tmpl_env1" + + // --- EC2 Instances Configuration --- + gateway_name = "asg_gateway" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + instances_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Auto Scaling Configuration --- + minimum_group_size = 2 + maximum_group_size = 10 + target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_instance_connect = false + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Outbound Proxy Configuration (optional) --- + proxy_elb_type = "internet-facing" + proxy_elb_clients = "0.0.0.0/0" + proxy_elb_port = 8080 + ``` + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To create an ASG configuration without a proxy ELB: + ``` + proxy_elb_type= "none" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|----------------------------|----------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_ids | List of public subnet IDs to launch resources into. Recommended at least 2 | list(string) | n/a | n/a | yes | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| management_server | The name that represents the Security Management Server in the CME configuration | string | n/a | n/a | yes | +| configuration_template | Name of the provisioning template in the CME configuration | string | n/a | n/a | yes | +| gateway_name | The name tag of the Security Gateways instances | string | n/a | Check-Point-ASG-gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| instances_tags | (Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances | map(string) | n/a | {} | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| minimum_group_size | The minimum number of instances in the Auto Scaling group | number | n/a | 2 | no | +| maximum_group_size | The maximum number of instances in the Auto Scaling group | number | n/a | 10 | no | +| target_groups | (Optional) List of Target Group ARNs to associate with the Auto Scaling group | list(string) | n/a | [] | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters) | string | n/a | "12345678" | yes | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| proxy_elb_type | Type of ELB to create as an HTTP/HTTPS outbound proxy | string | - none
- internal
- internet-facing | none | no | +| proxy_elb_port | The TCP port on which the proxy will be listening | number | n/a | 8080 | no | +| proxy_elb_clients | The CIDR range of the clients of the proxy | string | n/a | 0.0.0.0/0 | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|------------------------------------------------|-------------------------------------------------------------------| +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_autoscaling_group_availability_zones | The AZs on which the Autoscaling Group is configured | +| autoscale_autoscaling_group_desired_capacity | The deployed AutoScaling Group's desired capacity of instances | +| autoscale_autoscaling_group_min_size | The deployed AutoScaling Group's minimum number of instances | +| autoscale_autoscaling_group_max_size | The deployed AutoScaling Group's maximum number of instances | +| autoscale_autoscaling_group_load_balancers | The deployed AutoScaling Group's configured load balancers | +| autoscale_autoscaling_group_target_group_arns | The deployed AutoScaling Group's configured target groups | +| autoscale_autoscaling_group_subnets | The subnets on which the deployed AutoScaling Group is configured | +| autoscale_launch_template_id | The id of the Launch Template | +| autoscale_autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240417 | - Add support for Elastic Load Balancer Health Checks.
- EC2 Auto Scaling will start to detect and act on health checks performed by Elastic Load Balancing. | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | Change default shell for the admin user to /etc/cli.sh | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | AWS Terraform modules refactor | +| 20200318 | First release of Check Point Auto Scaling Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/autoscale/asg_userdata.yaml b/deprecated/terraform/aws/R80.40/autoscale/asg_userdata.yaml new file mode 100755 index 00000000..ea6de749 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/asg_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" installationType=\"autoscale\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"autoscale\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" bootstrapScript64=\"${BootstrapScript}\" diff --git a/deprecated/terraform/aws/R80.40/autoscale/locals.tf b/deprecated/terraform/aws/R80.40/autoscale/locals.tf new file mode 100755 index 00000000..72fa5951 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/locals.tf @@ -0,0 +1,62 @@ +locals { + asg_name = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.asg_name) + create_iam_role = var.enable_cloudwatch ? 1 : 0 + + gateways_provision_address_type_allowed_values = [ + "public", + "private" + ] + // Will fail if var.gateways_provision_address_type is invalid + validate_gateways_provision_address_type = index(local.gateways_provision_address_type_allowed_values, var.gateways_provision_address_type) + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh" + ] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SICKey] must be at least 8 alphanumeric characters" + + proxy_elb_type_allowed_values = [ + "none", + "internal", + "internet-facing" + ] + // Will fail if var.proxy_elb_type is invalid + validate_proxy_elb_type = index(local.proxy_elb_type_allowed_values, var.proxy_elb_type) + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.proxy_elb_clients is invalid + regex_cidr_result = regex(local.regex_valid_cidr_range, var.proxy_elb_clients) == var.proxy_elb_clients ? 0 : "Variable [proxy_elb_clients] must be a valid CIDR range" + + tags_asg_format = null_resource.tags_as_list_of_maps.*.triggers + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_password_hash_base64 = base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) +} +resource "null_resource" "tags_as_list_of_maps" { + count = length(keys(var.instances_tags)) + + triggers = { + "key" = keys(var.instances_tags)[count.index] + "value" = values(var.instances_tags)[count.index] + "propagate_at_launch" = "true" + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/autoscale/main.tf b/deprecated/terraform/aws/R80.40/autoscale/main.tf new file mode 100755 index 00000000..68abbfe0 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/main.tf @@ -0,0 +1,248 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version +} + +resource "aws_security_group" "permissive_sg" { + name_prefix = format("%s_PermissiveSecurityGroup", local.asg_name) + description = "Permissive security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + tags = { + Name = format("%s_PermissiveSecurityGroup", local.asg_name) + } +} + +resource "aws_launch_template" "asg_launch_template" { + name_prefix = local.asg_name + image_id = module.amis.ami_id + instance_type = var.gateway_instance_type + key_name = var.key_name + network_interfaces { + associate_public_ip_address = true + security_groups = [aws_security_group.permissive_sg.id] + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + iam_instance_profile { + name = ( var.enable_cloudwatch ? aws_iam_instance_profile.instance_profile[0].name : "") + } + monitoring { + enabled = true + } + + block_device_mappings { + device_name = "/dev/xvda" + ebs { + volume_type = "gp3" + volume_size = var.volume_size + encrypted = var.enable_volume_encryption + } + } + description = "Initial template version" + + + user_data = base64encode(templatefile("${path.module}/asg_userdata.yaml", { + // script's arguments + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + EnableCloudWatch = var.enable_cloudwatch, + EnableInstanceConnect = var.enable_instance_connect, + Shell = var.admin_shell, + SICKey = local.gateway_SICkey_base64, + AllowUploadDownload = var.allow_upload_download, + BootstrapScript = local.gateway_bootstrap_script64, + OsVersion = local.version_split + })) +} +resource "aws_autoscaling_group" "asg" { + name_prefix = local.asg_name + launch_template { + id = aws_launch_template.asg_launch_template.id + version = aws_launch_template.asg_launch_template.latest_version + } + min_size = var.minimum_group_size + max_size = var.maximum_group_size + load_balancers = aws_elb.proxy_elb.*.name + target_group_arns = var.target_groups + vpc_zone_identifier = var.subnet_ids + health_check_grace_period = 3600 + health_check_type = "ELB" + + tag { + key = "Name" + value = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.gateway_name) + propagate_at_launch = true + } + + tag { + key = "x-chkp-tags" + value = format("management=%s:template=%s:ip-address=%s", var.management_server, var.configuration_template, var.gateways_provision_address_type) + propagate_at_launch = true + } + + dynamic "tag" { + for_each = var.instances_tags + content { + key = tag.key + value = tag.value + propagate_at_launch = true + } + } +} + +data "aws_iam_policy_document" "assume_role_policy_document" { + version = "2012-10-17" + statement { + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + effect = "Allow" + } +} + +resource "aws_iam_role" "role" { + count = local.create_iam_role + name_prefix = format("%s-iam_role", local.asg_name) + assume_role_policy = data.aws_iam_policy_document.assume_role_policy_document.json + path = "/" +} +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.create_iam_role + role = aws_iam_role.role[count.index].name + tag_name = local.asg_name +} + +resource "aws_iam_instance_profile" "instance_profile" { + count = local.create_iam_role + name_prefix = format("%s-iam_instance_profile", local.asg_name) + path = "/" + role = aws_iam_role.role[count.index].name +} + +// Proxy ELB +locals { + proxy_elb_condition = var.proxy_elb_type != "none" ? 1 : 0 +} +resource "random_id" "proxy_elb_uuid" { + byte_length = 5 +} +resource "aws_elb" "proxy_elb" { + count = local.proxy_elb_condition + name = format("%s-proxy-elb-%s", var.prefix, random_id.proxy_elb_uuid.hex) + internal = var.proxy_elb_type == "internal" + cross_zone_load_balancing = true + listener { + instance_port = var.proxy_elb_port + instance_protocol = "TCP" + lb_port = var.proxy_elb_port + lb_protocol = "TCP" + } + health_check { + target = format("TCP:%s", var.proxy_elb_port) + healthy_threshold = 3 + unhealthy_threshold = 5 + interval = 30 + timeout = 5 + } + subnets = var.subnet_ids + security_groups = [aws_security_group.elb_security_group[count.index].id] +} +resource "aws_load_balancer_policy" "proxy_elb_policy" { + count = local.proxy_elb_condition + load_balancer_name = aws_elb.proxy_elb[count.index].name + policy_name = "EnableProxyProtocol" + policy_type_name = "ProxyProtocolPolicyType" + + policy_attribute { + name = "ProxyProtocol" + value = "true" + } +} +resource "aws_security_group" "elb_security_group" { + count = local.proxy_elb_condition + description = "ELB security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + protocol = "tcp" + cidr_blocks = [var.proxy_elb_clients] + from_port = var.proxy_elb_port + to_port = var.proxy_elb_port + } +} + +// Scaling metrics +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_low" { + alarm_name = format("%s_alarm_low", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-down if CPU < 60% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 60 + alarm_actions = [aws_autoscaling_policy.scale_down_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "LessThanThreshold" +} +resource "aws_autoscaling_policy" "scale_down_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_down", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = -1 +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_high" { + alarm_name = format("%s_alarm_high", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-up if CPU > 80% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 80 + alarm_actions = [aws_autoscaling_policy.scale_up_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "GreaterThanThreshold" +} +resource "aws_autoscaling_policy" "scale_up_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_up", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = 1 +} diff --git a/deprecated/terraform/aws/R80.40/autoscale/output.tf b/deprecated/terraform/aws/R80.40/autoscale/output.tf new file mode 100755 index 00000000..152bb744 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/output.tf @@ -0,0 +1,43 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} + +output "autoscale_autoscaling_group_name" { + value = aws_autoscaling_group.asg.name +} +output "autoscale_autoscaling_group_arn" { + value = aws_autoscaling_group.asg.arn +} +output "autoscale_autoscaling_group_availability_zones" { + value = aws_autoscaling_group.asg.availability_zones +} +output "autoscale_autoscaling_group_desired_capacity" { + value = aws_autoscaling_group.asg.desired_capacity +} +output "autoscale_autoscaling_group_min_size" { + value = aws_autoscaling_group.asg.min_size +} +output "autoscale_autoscaling_group_max_size" { + value = aws_autoscaling_group.asg.max_size +} +output "autoscale_autoscaling_group_load_balancers" { + value = aws_autoscaling_group.asg.load_balancers +} +output "autoscale_autoscaling_group_target_group_arns" { + value = aws_autoscaling_group.asg.target_group_arns +} +output "autoscale_autoscaling_group_subnets" { + value = aws_autoscaling_group.asg.vpc_zone_identifier +} +output "autoscale_launch_template_id" { + value = aws_launch_template.asg_launch_template.id +} + +output "autoscale_security_group_id" { + value = aws_security_group.permissive_sg.id +} + +output "autoscale_iam_role_name" { + value = aws_iam_role.role.*.name +} + diff --git a/deprecated/terraform/aws/R80.40/autoscale/terraform.tfvars b/deprecated/terraform/aws/R80.40/autoscale/terraform.tfvars new file mode 100755 index 00000000..d513fcd5 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/terraform.tfvars @@ -0,0 +1,45 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "env1" +asg_name = "autoscaling_group" + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_ids = ["subnet-abc123", "subnet-def456"] + +// --- Automatic Provisioning with Security Management Server Settings --- +gateways_provision_address_type = "private" +management_server = "mgmt_env1" +configuration_template = "tmpl_env1" + +// --- EC2 Instances Configuration --- +gateway_name = "asg_gateway" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +instances_tags = { + key1 = "value1" + key2 = "value2" +} +metadata_imdsv2_required = true + +// --- Auto Scaling Configuration --- +minimum_group_size = 2 +maximum_group_size = 10 +target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_instance_connect = false +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Outbound Proxy Configuration (optional) --- +proxy_elb_type = "internet-facing" +proxy_elb_clients = "0.0.0.0/0" +proxy_elb_port = 8080 diff --git a/deprecated/terraform/aws/R80.40/autoscale/variables.tf b/deprecated/terraform/aws/R80.40/autoscale/variables.tf new file mode 100755 index 00000000..81d256ab --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/variables.tf @@ -0,0 +1,190 @@ +// Module: Check Point CloudGuard Network Auto Scaling Group into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. Recommended at least 2" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the CME configuration" +} +variable "configuration_template" { + type = string + description = "Name of the provisioning template in the CME configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} + +// --- EC2 Instances Configuration --- +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateways instances" + default = "Check-Point-ASG-gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "instances_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances" + default = {} +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} + +// --- Auto Scaling Configuration --- +variable "minimum_group_size" { + type = number + description = "The minimum number of instances in the Auto Scaling group" + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximum number of instances in the Auto Scaling group" + default = 10 +} +variable "target_groups" { + type = list(string) + description = "(Optional) List of Target Group ARNs to associate with the Auto Scaling group" + default = [] +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- (Optional) Outbound Proxy Configuration --- +variable "proxy_elb_type" { + type = string + description = "Type of ELB to create as an HTTP/HTTPS outbound proxy" + default = "none" +} +variable "proxy_elb_port" { + type = number + description = "The TCP port on which the proxy will be listening" + default = 8080 +} +variable "proxy_elb_clients" { + type = string + description = "The CIDR range of the clients of the proxy" + default = "0.0.0.0/0" +} diff --git a/deprecated/terraform/aws/R80.40/autoscale/versions.tf b/deprecated/terraform/aws/R80.40/autoscale/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/autoscale/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/cluster-master/README.md b/deprecated/terraform/aws/R80.40/cluster-master/README.md new file mode 100755 index 00000000..ece3775c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster-master/README.md @@ -0,0 +1,221 @@ +# Check Point CloudGuard Network Security Cluster Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cluster into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk104418) for additional information + +This solution uses the following modules: +- /terraform/aws/cluster +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/cluster-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + } + private_subnets_map = { + "us-east-1a" = 2 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint module.launch_cluster_into_vpc.aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|--------------------|-----------------------------------------------------| +| ami_id | The ami id of the deployed Security Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Cluster Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/cluster-master/locals.tf b/deprecated/terraform/aws/R80.40/cluster-master/locals.tf new file mode 100755 index 00000000..b77484fe --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster-master/locals.tf @@ -0,0 +1,52 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" +} diff --git a/deprecated/terraform/aws/R80.40/cluster-master/main.tf b/deprecated/terraform/aws/R80.40/cluster-master/main.tf new file mode 100755 index 00000000..29746863 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster-master/main.tf @@ -0,0 +1,64 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} +module "launch_cluster_into_vpc" { + source = "../cluster" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_id = module.launch_vpc.public_subnets_ids_list[0] + private_subnet_id = module.launch_vpc.private_subnets_ids_list[0] + private_route_table = aws_route_table.private_subnet_rtb.id + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + memberAToken = var.memberAToken + memberBToken = var.memberBToken + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp +} diff --git a/deprecated/terraform/aws/R80.40/cluster-master/output.tf b/deprecated/terraform/aws/R80.40/cluster-master/output.tf new file mode 100755 index 00000000..c1f47385 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster-master/output.tf @@ -0,0 +1,24 @@ +output "ami_id" { + value = module.launch_cluster_into_vpc.ami_id +} +output "cluster_public_ip" { + value = module.launch_cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.launch_cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.launch_cluster_into_vpc.member_b_public_ip +} +output "member_a_ssh" { + value = module.launch_cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.launch_cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.launch_cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.launch_cluster_into_vpc.member_b_url +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cluster-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/cluster-master/terraform.tfvars new file mode 100755 index 00000000..1e7b2c78 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster-master/terraform.tfvars @@ -0,0 +1,47 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 +} +private_subnets_map = { + "us-east-1a" = 2 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cluster-master/variables.tf b/deprecated/terraform/aws/R80.40/cluster-master/variables.tf new file mode 100755 index 00000000..d1faf72c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster-master/variables.tf @@ -0,0 +1,183 @@ +// Module: Check Point CloudGuard Network Security Cluster into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R80.40/cluster-master/versions.tf b/deprecated/terraform/aws/R80.40/cluster-master/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/cluster/README.md b/deprecated/terraform/aws/R80.40/cluster/README.md new file mode 100755 index 00000000..2290fdb7 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/README.md @@ -0,0 +1,201 @@ +# Check Point CloudGuard Network Security Cluster Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cluster into an existing VPC on AWS. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk104418) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_id = "subnet-123456" + private_subnet_id = "subnet-345678" + private_route_table = "rtb-12345678" + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the cluster. The cluster's public IPs will be generated from this subnet | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the cluster. The cluster's private IPs will be generated from this subnet | string | n/a | n/a | yes | +| private_route_table | (Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|--------------------|-----------------------------------------------------| +| ami_id | The ami id of the deployed Security Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240304 | Add x-chkp-cluster-ips, x-chkp-member-ips tags to cluster members | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Cluster Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/cluster/cluster_member_a_userdata.yaml b/deprecated/terraform/aws/R80.40/cluster/cluster_member_a_userdata.yaml new file mode 100755 index 00000000..6329e2cf --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/cluster_member_a_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenA}\"" installationType=\"cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" elasticIp=\"${MemberAPublicAddress}\" templateVersion=\"20231012\" templateName=\"cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" allocatePublicAddress=\"${AllocateAddress}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cluster/cluster_member_b_userdata.yaml b/deprecated/terraform/aws/R80.40/cluster/cluster_member_b_userdata.yaml new file mode 100755 index 00000000..36d29dc5 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/cluster_member_b_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenB}\"" installationType=\"cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" elasticIp=\"${MemberBPublicAddress}\" templateVersion=\"20231012\" templateName=\"cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" allocatePublicAddress=\"${AllocateAddress}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cluster/locals.tf b/deprecated/terraform/aws/R80.40/cluster/locals.tf new file mode 100755 index 00000000..d64b39e7 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/locals.tf @@ -0,0 +1,69 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + create_iam_role = var.predefined_role == "" ? 1 : 0 + provided_roue_table = var.private_route_table == "" ? 0 : 1 + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + //TokenA: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenA = split(" ", var.memberAToken) + tokenA_decode = base64decode(element(local.split_tokenA, length(local.split_tokenA)-1)) + regex_tokenA = regex(local.regex_token_valid, local.tokenA_decode) == local.tokenA_decode ? 0 : "Smart-1 Cloud token A is invalid format" + + //TokenB: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenB = split(" ", var.memberBToken) + tokenB_decode = base64decode(element(local.split_tokenB, length(local.split_tokenB)-1)) + regex_tokenB = regex(local.regex_token_valid, local.tokenB_decode) == local.tokenB_decode ? 0 : "Smart-1 Cloud token B is invalid format" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) + gateway_password_hash_base64=base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) +} diff --git a/deprecated/terraform/aws/R80.40/cluster/main.tf b/deprecated/terraform/aws/R80.40/cluster/main.tf new file mode 100755 index 00000000..8282b24b --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/main.tf @@ -0,0 +1,291 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +resource "aws_iam_instance_profile" "cluster_instance_profile" { + path = "/" + role = local.create_iam_role == 1 ? join("", module.cluster_iam_role.*.cluster_iam_role_name) : var.predefined_role +} + +module "cluster_iam_role" { + source = "../modules/cluster-iam-role" + count = local.create_iam_role +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_instance_profile.cluster_instance_profile.role + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name +} + +resource "aws_network_interface" "member_a_external_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A external" + source_dest_check = false + lifecycle { + ignore_changes = [private_ips_count,] + } + private_ips_count = 1 + tags = { + Name = format("%s-Member_A_ExternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_network_interface" "member_b_external_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B external" + source_dest_check = false + tags = { + Name = format("%s-Member_B_ExternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_network_interface" "member_a_internal_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A internal" + source_dest_check = false + lifecycle { + ignore_changes = [private_ips_count,] + } + private_ips_count = 1 + tags = { + Name = format("%s-Member_A_InternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_network_interface" "member_b_internal_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B internal" + source_dest_check = false + tags = { + Name = format("%s-Member_B_InternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_route" "internal_default_route" { + count = local.internal_route_table_condition + route_table_id = var.private_route_table + lifecycle { + ignore_changes = [network_interface_id,] + } + destination_cidr_block = "0.0.0.0/0" + network_interface_id = aws_network_interface.member_a_internal_eni.id +} + +resource "aws_route_table_association" "private_rtb_to_private_subnet" { + count = var.private_route_table == "" ? 0 : 1 + route_table_id = var.private_route_table + subnet_id = var.private_subnet_id +} + +resource "aws_launch_template" "member_a_launch_template" { + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_a_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_a_internal_eni.id + device_index = 1 + } +} + +resource "aws_launch_template" "member_b_launch_template" { + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_b_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_b_internal_eni.id + device_index = 1 + } +} + +resource "aws_instance" "member-a-instance" { + depends_on = [ + aws_network_interface.member_a_external_eni, + aws_network_interface.member_a_internal_eni + ] + + launch_template { + id = aws_launch_template.member_a_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-A",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + var.allocate_and_associate_eip ? aws_eip.member_a_eip[0].public_ip : "", aws_network_interface.member_a_external_eni.private_ip,aws_network_interface.member_a_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:cluster-eth0-private-ip=%s:cluster-eth1-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0), + element(tolist(setsubtract(tolist(aws_network_interface.member_a_internal_eni.private_ips), [aws_network_interface.member_a_internal_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_a_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenA = var.memberAToken, + MemberAPublicAddress = var.allocate_and_associate_eip ? aws_eip.member_a_eip[0].public_ip : "", + AllocateAddress = var.allocate_and_associate_eip, + OsVersion = local.version_split + }) +} + +resource "aws_instance" "member-b-instance" { + depends_on = [ + aws_network_interface.member_b_external_eni, + aws_network_interface.member_b_internal_eni + ] + + launch_template { + id = aws_launch_template.member_b_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-B",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + var.allocate_and_associate_eip ? aws_eip.member_b_eip[0].public_ip : "", aws_network_interface.member_b_external_eni.private_ip,aws_network_interface.member_b_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:cluster-eth0-private-ip=%s:cluster-eth1-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0), + element(tolist(setsubtract(tolist(aws_network_interface.member_a_internal_eni.private_ips), [aws_network_interface.member_a_internal_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_b_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenB = var.memberBToken, + MemberBPublicAddress = var.allocate_and_associate_eip ? aws_eip.member_b_eip[0].public_ip : "", + AllocateAddress = var.allocate_and_associate_eip, + OsVersion = local.version_split + }) +} + +resource "aws_eip" "cluster_eip" { +} + +resource "aws_eip" "member_a_eip" { + count = var.allocate_and_associate_eip ? 1 : 0 +} + +resource "aws_eip" "member_b_eip" { + count = var.allocate_and_associate_eip ? 1 : 0 +} + +resource "aws_eip_association" "cluster_address_assoc" { + depends_on = [aws_instance.member-a-instance] + allocation_id = aws_eip.cluster_eip.id + lifecycle { + ignore_changes = [ + network_interface_id, private_ip_address + ] + } + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : ""//extracting member's secondary ip which represent the cluster ip +} +resource "aws_eip_association" "member_a_address_assoc" { + depends_on = [aws_instance.member-a-instance] + count = var.allocate_and_associate_eip ? 1 : 0 + allocation_id = aws_eip.member_a_eip[0].id + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = aws_network_interface.member_a_external_eni.private_ip //primary +} +resource "aws_eip_association" "member_b_address_assoc" { + depends_on = [aws_instance.member-b-instance] + count = var.allocate_and_associate_eip ? 1 : 0 + allocation_id = aws_eip.member_b_eip[0].id + network_interface_id = aws_network_interface.member_b_external_eni.id + private_ip_address = aws_network_interface.member_b_external_eni.private_ip //primary +} + diff --git a/deprecated/terraform/aws/R80.40/cluster/output.tf b/deprecated/terraform/aws/R80.40/cluster/output.tf new file mode 100755 index 00000000..6e8f5cbf --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/output.tf @@ -0,0 +1,24 @@ +output "ami_id" { + value = module.amis.ami_id +} +output "cluster_public_ip" { + value = aws_eip.cluster_eip.*.public_ip +} +output "member_a_public_ip" { + value = aws_eip.member_a_eip.*.public_ip +} +output "member_b_public_ip" { + value = aws_eip.member_b_eip.*.public_ip +} +output "member_a_ssh" { + value = var.allocate_and_associate_eip ? format("ssh -i %s admin@%s", var.key_name, aws_eip.member_a_eip[0].public_ip) : "" +} +output "member_b_ssh" { + value = var.allocate_and_associate_eip ? format("ssh -i %s admin@%s", var.key_name, aws_eip.member_b_eip[0].public_ip) : "" +} +output "member_a_url" { + value = var.allocate_and_associate_eip ? format("https://%s", aws_eip.member_a_eip[0].public_ip) : "" +} +output "member_b_url" { + value = var.allocate_and_associate_eip ? format("https://%s", aws_eip.member_b_eip[0].public_ip) : "" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cluster/terraform.tfvars b/deprecated/terraform/aws/R80.40/cluster/terraform.tfvars new file mode 100755 index 00000000..179fe10b --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_id = "subnet-123456" +private_subnet_id = "subnet-345678" +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cluster/variables.tf b/deprecated/terraform/aws/R80.40/cluster/variables.tf new file mode 100755 index 00000000..1b515744 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/variables.tf @@ -0,0 +1,181 @@ +// Module: Check Point CloudGuard Network Security Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_id" { + type = string + description = "The public subnet of the cluster. The cluster's public IPs will be generated from this subnet" +} +variable "private_subnet_id" { + type = string + description = "The private subnet of the cluster. The cluster's private IPs will be generated from this subnet" +} +variable "private_route_table" { + type = string + description = "(Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R80.40/cluster/versions.tf b/deprecated/terraform/aws/R80.40/cluster/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cluster/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/README.md b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/README.md new file mode 100755 index 00000000..ae261614 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/README.md @@ -0,0 +1,100 @@ +# AWS IAM Role for Cloud Management Extension (CME) manages Gateway Load Balancer Auto Scale Group Terraform module + +Terraform module which creates an AWS IAM Role for Cloud Management Extension (CME) manages Gateway Load Balancer Auto Scale Group on Security Management Server. + +These types of Terraform resources are supported: +* [AWS IAM role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) +* [AWS IAM policy](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_policy) +* [AWS IAM policy attachment](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role_policy_attachment) + +This type of Terraform data source is supported: +* [AWS IAM policy document](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/iam_policy_document) + +See the [Creating an AWS IAM Role for Security Management Server](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk122074) for additional information + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cme-iam-role-gwlb/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cme-iam-role-gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cme-iam-role-gwlb/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + permissions = "Create with read permissions" + sts_roles = ['arn:aws:iam::111111111111:role/role_name'] + trusted_account = "" + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-----------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| permissions | The IAM role permissions | string | - Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| sts_roles | The IAM role will be able to assume these STS Roles (map of string ARNs) | list(string) | n/a | [] | no | +| trusted_account | A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|----------------------|---------------------------------------| +| cme_iam_role_arn | The created AWS IAM Role arn | +| cme_iam_role_name | The created AWS IAM Role name | +| cme_iam_profile_name | The created AWS instance profile name | +| cme_iam_profile_arn | The created AWS instance profile arn | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|--------------------------------------------------------------------| +| 20240507 | Add ec2:DescribeRegions read permission to the IAM role policy | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230926 | CME instance profile for IAM Role | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/main.tf b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/main.tf new file mode 100755 index 00000000..33ea37ab --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/main.tf @@ -0,0 +1,110 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +resource "aws_iam_role" "cme_iam_role_gwlb" { + assume_role_policy = data.aws_iam_policy_document.cme_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "cme_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = var.trusted_account == "" ? "Service" : "AWS" + identifiers = var.trusted_account == "" ? ["ec2.amazonaws.com"] : [var.trusted_account] + } + } +} + +locals { + provided_sts_roles = length(var.sts_roles) == 0 ? 0 : 1 + allow_read_permissions = var.permissions == "Create with read-write permissions" || var.permissions == "Create with read permissions" ? 1 : 0 + allow_write_permissions = var.permissions == "Create with read-write permissions" ? 1 : 0 +} + +data "aws_iam_policy_document" "cme_role_sts_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + resources = var.sts_roles + } +} +resource "aws_iam_policy" "cme_role_sts_policy" { + count = local.provided_sts_roles + policy = data.aws_iam_policy_document.cme_role_sts_policy_doc.json + +} +resource "aws_iam_role_policy_attachment" "attach_sts_policy" { + count = local.provided_sts_roles + policy_arn = aws_iam_policy.cme_role_sts_policy[0].arn + role = aws_iam_role.cme_iam_role_gwlb.id +} + +data "aws_iam_policy_document" "cme_role_read_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "autoscaling:DescribeAutoScalingGroups", + "ec2:DescribeRegions", + "ec2:DescribeInstances", + "ec2:DescribeNetworkInterfaces", + "ec2:DescribeRouteTables", + "ec2:DescribeSecurityGroups", + "ec2:DescribeSubnets", + "ec2:DescribeVpcs", + "ec2:DescribeInternetGateways", + "ec2:DescribeVpcEndpoints", + "ec2:DescribeVpcEndpointServiceConfigurations", + "elasticloadbalancing:DescribeLoadBalancers", + "elasticloadbalancing:DescribeTags", + "elasticloadbalancing:DescribeListeners", + "elasticloadbalancing:DescribeTargetGroups", + "elasticloadbalancing:DescribeRules", + "elasticloadbalancing:DescribeTargetHealth"] + resources = ["*"] + } +} +resource "aws_iam_policy" "cme_role_read_policy" { + count = local.allow_read_permissions + policy = data.aws_iam_policy_document.cme_role_read_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_read_policy" { + count = local.allow_read_permissions + policy_arn = aws_iam_policy.cme_role_read_policy[0].arn + role = aws_iam_role.cme_iam_role_gwlb.id +} + +data "aws_iam_policy_document" "cme_role_write_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "ec2:CreateRoute", + "ec2:ReplaceRoute", + "ec2:DeleteRoute", + "ec2:CreateRouteTable", + "ec2:AssociateRouteTable", + "ec2:CreateTags" +] + resources = ["*"] + } +} +resource "aws_iam_policy" "cme_role_write_policy" { + count = local.allow_write_permissions + policy = data.aws_iam_policy_document.cme_role_write_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_write_policy" { + count = local.allow_write_permissions + policy_arn = aws_iam_policy.cme_role_write_policy[0].arn + role = aws_iam_role.cme_iam_role_gwlb.id +} +resource "aws_iam_instance_profile" "iam_instance_profile" { + role = aws_iam_role.cme_iam_role_gwlb.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/output.tf b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/output.tf new file mode 100755 index 00000000..8c86901a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/output.tf @@ -0,0 +1,13 @@ +output "cme_iam_role_arn" { + value = aws_iam_role.cme_iam_role_gwlb.arn +} +output "cme_iam_role_name" { + value = aws_iam_role.cme_iam_role_gwlb.name +} +output "cme_iam_profile_name" { + value = aws_iam_instance_profile.iam_instance_profile.name +} +output "cme_iam_profile_arn" { + value = aws_iam_instance_profile.iam_instance_profile.arn +} + diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/terraform.tfvars b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/terraform.tfvars new file mode 100755 index 00000000..9914eae9 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/terraform.tfvars @@ -0,0 +1,5 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +permissions = "Create with read permissions" +sts_roles = [] +trusted_account = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/variables.tf b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/variables.tf new file mode 100755 index 00000000..3a0fe740 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/variables.tf @@ -0,0 +1,42 @@ +// Module: IAM role for selected permissions + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +variable "permissions" { + type = string + description = "The IAM role permissions" + default = "Create with read permissions" +} +locals { + permissions_allowed_values = [ + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.permissions) +} +variable "sts_roles" { + type = list(string) + description = "The IAM role will be able to assume these STS Roles (map of string ARNs)" + default = [] +} +variable "trusted_account" { + type = string + description = "A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it" + default = "" +} diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/versions.tf b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/versions.tf new file mode 100755 index 00000000..b3e24059 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role-gwlb/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role/README.md b/deprecated/terraform/aws/R80.40/cme-iam-role/README.md new file mode 100755 index 00000000..5aa02a68 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role/README.md @@ -0,0 +1,102 @@ +# AWS IAM Role for Cloud Management Extension (CME) Terraform module + +Terraform module which creates an AWS IAM Role for Cloud Management Extension (CME) on Security Management Server. + +These types of Terraform resources are supported: +* [AWS IAM role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) +* [AWS IAM policy](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_policy) +* [AWS IAM policy attachment](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role_policy_attachment) + +This type of Terraform data source is supported: +* [AWS IAM policy document](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/iam_policy_document) + +See the [Creating an AWS IAM Role for Security Management Server](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk122074) for additional information + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cme-iam-role/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cme-iam-role/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cme-iam-role/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + permissions = "Create with read permissions" + sts_roles = ['arn:aws:iam::111111111111:role/role_name'] + trusted_account = "" + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-----------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| permissions | The IAM role permissions | string | - Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| sts_roles | The IAM role will be able to assume these STS Roles (map of string ARNs) | list(string) | n/a | [] | no | +| trusted_account | A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|----------------------|---------------------------------------| +| cme_iam_role_arn | The created AWS IAM Role arn | +| cme_iam_role_name | The created AWS IAM Role name | +| cme_iam_profile_name | The created AWS instance profile name | +| cme_iam_profile_arn | The created AWS instance profile arn | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|--------------------------------------------------------------------| +| 20240507 | Add ec2:DescribeRegions read permission to the IAM role policy | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230514 | CME instance profile for IAM Role | +| 20210309 | First release of Check Point CME IAM Role Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role/main.tf b/deprecated/terraform/aws/R80.40/cme-iam-role/main.tf new file mode 100755 index 00000000..817e3b90 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role/main.tf @@ -0,0 +1,136 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +resource "aws_iam_role" "cme_iam_role" { + assume_role_policy = data.aws_iam_policy_document.cme_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "cme_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = var.trusted_account == "" ? "Service" : "AWS" + identifiers = var.trusted_account == "" ? ["ec2.amazonaws.com"] : [var.trusted_account] + } + } +} + +locals { + provided_sts_roles = length(var.sts_roles) == 0 ? 0 : 1 + allow_read_permissions = var.permissions == "Create with read-write permissions" || var.permissions == "Create with read permissions" ? 1 : 0 + allow_write_permissions = var.permissions == "Create with read-write permissions" ? 1 : 0 +} + +data "aws_iam_policy_document" "cme_role_sts_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + resources = var.sts_roles + } +} +resource "aws_iam_policy" "cme_role_sts_policy" { + count = local.provided_sts_roles + policy = data.aws_iam_policy_document.cme_role_sts_policy_doc.json + +} +resource "aws_iam_role_policy_attachment" "attach_sts_policy" { + count = local.provided_sts_roles + policy_arn = aws_iam_policy.cme_role_sts_policy[0].arn + role = aws_iam_role.cme_iam_role.id +} + +data "aws_iam_policy_document" "cme_role_read_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "autoscaling:DescribeAutoScalingGroups", + "ec2:DescribeRegions", + "ec2:DescribeCustomerGateways", + "ec2:DescribeInstances", + "ec2:DescribeNetworkInterfaces", + "ec2:DescribeRouteTables", + "ec2:DescribeSecurityGroups", + "ec2:DescribeSubnets", + "ec2:DescribeTransitGateways", + "ec2:DescribeTransitGatewayAttachments", + "ec2:DescribeTransitGatewayRouteTables", + "ec2:DescribeVpcs", + "ec2:DescribeVpnGateways", + "ec2:DescribeVpnConnections", + "ec2:GetTransitGatewayAttachmentPropagations", + "elasticloadbalancing:DescribeLoadBalancers", + "elasticloadbalancing:DescribeTags", + "elasticloadbalancing:DescribeListeners", + "elasticloadbalancing:DescribeTargetGroups", + "elasticloadbalancing:DescribeRules", + "elasticloadbalancing:DescribeTargetHealth"] + resources = ["*"] + } +} +resource "aws_iam_policy" "cme_role_read_policy" { + count = local.allow_read_permissions + policy = data.aws_iam_policy_document.cme_role_read_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_read_policy" { + count = local.allow_read_permissions + policy_arn = aws_iam_policy.cme_role_read_policy[0].arn + role = aws_iam_role.cme_iam_role.id +} + +data "aws_iam_policy_document" "cme_role_write_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "ec2:AssociateTransitGatewayRouteTable", + "ec2:AttachVpnGateway", + "ec2:CreateCustomerGateway", + "ec2:CreateVpnConnection", + "ec2:CreateVpnGateway", + "ec2:DeleteCustomerGateway", + "ec2:DeleteVpnConnection", + "ec2:DeleteVpnGateway", + "ec2:DetachVpnGateway", + "ec2:DisableTransitGatewayRouteTablePropagation", + "ec2:DisableVgwRoutePropagation", + "ec2:DisassociateTransitGatewayRouteTable", + "ec2:EnableTransitGatewayRouteTablePropagation", + "ec2:EnableVgwRoutePropagation"] + resources = ["*"] + } + statement { + effect = "Allow" + actions = [ + "cloudformation:DescribeStacks", + "cloudformation:DescribeStackResources", + "cloudformation:ListStacks"] + resources = ["*"] + } + statement { + effect = "Allow" + actions = [ + "cloudformation:CreateStack", + "cloudformation:DeleteStack"] + resources = ["arn:aws:cloudformation:*:*:stack/vpn-by-tag--*/*"] + } +} +resource "aws_iam_policy" "cme_role_write_policy" { + count = local.allow_write_permissions + policy = data.aws_iam_policy_document.cme_role_write_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_write_policy" { + count = local.allow_write_permissions + policy_arn = aws_iam_policy.cme_role_write_policy[0].arn + role = aws_iam_role.cme_iam_role.id +} +resource "aws_iam_instance_profile" "iam_instance_profile" { + role = aws_iam_role.cme_iam_role.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role/output.tf b/deprecated/terraform/aws/R80.40/cme-iam-role/output.tf new file mode 100755 index 00000000..cad35709 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role/output.tf @@ -0,0 +1,12 @@ +output "cme_iam_role_arn" { + value = aws_iam_role.cme_iam_role.arn +} +output "cme_iam_role_name" { + value = aws_iam_role.cme_iam_role.name +} +output "cme_iam_profile_name" { + value = aws_iam_instance_profile.iam_instance_profile.name +} +output "cme_iam_profile_arn" { + value = aws_iam_instance_profile.iam_instance_profile.arn +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role/terraform.tfvars b/deprecated/terraform/aws/R80.40/cme-iam-role/terraform.tfvars new file mode 100755 index 00000000..9914eae9 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role/terraform.tfvars @@ -0,0 +1,5 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +permissions = "Create with read permissions" +sts_roles = [] +trusted_account = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role/variables.tf b/deprecated/terraform/aws/R80.40/cme-iam-role/variables.tf new file mode 100755 index 00000000..3a0fe740 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role/variables.tf @@ -0,0 +1,42 @@ +// Module: IAM role for selected permissions + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +variable "permissions" { + type = string + description = "The IAM role permissions" + default = "Create with read permissions" +} +locals { + permissions_allowed_values = [ + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.permissions) +} +variable "sts_roles" { + type = list(string) + description = "The IAM role will be able to assume these STS Roles (map of string ARNs)" + default = [] +} +variable "trusted_account" { + type = string + description = "A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it" + default = "" +} diff --git a/deprecated/terraform/aws/R80.40/cme-iam-role/versions.tf b/deprecated/terraform/aws/R80.40/cme-iam-role/versions.tf new file mode 100755 index 00000000..b3e24059 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cme-iam-role/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster-master/README.md b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/README.md new file mode 100755 index 00000000..1a27cedc --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/README.md @@ -0,0 +1,219 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster into into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/cross-az-cluster +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cross-az-cluster-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cross-az-cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cross-az-cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cross-az-cluster-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/cross-az-cluster-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + private_subnets_map = { + "us-east-1a" = 3 + "us-east-1a" = 4 + } + subnets_bit_length = 8 + + + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create IAM Role: + ``` + predefined_role = "" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint module.launch_cluster_into_vpc.aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1 \"us-east-1b\" = 2} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3 \"us-east-1b\" = 4} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX - R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|--------------------|--------------------------------------------------------------| +| ami_id | The ami id of the deployed Security Cross AZ Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221123 | R81.20 version support | +| 20221123 | Changed default version and added instances types | +| 20221123 | First release of Check Point Security Cross AZ Cluster Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../cross-az/LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster-master/locals.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/locals.tf new file mode 100755 index 00000000..68e4523f --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/locals.tf @@ -0,0 +1,58 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster-master/main.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/main.tf new file mode 100755 index 00000000..f12ae536 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/main.tf @@ -0,0 +1,70 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets_a" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} +resource "aws_route_table_association" "private_rtb_to_private_subnets_b" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[1] +} + +module "launch_cluster_into_vpc" { + source = "../cross-az-cluster" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_ids = module.launch_vpc.public_subnets_ids_list + private_subnet_ids = module.launch_vpc.private_subnets_ids_list + private_route_table = aws_route_table.private_subnet_rtb.id + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + memberAToken = var.memberAToken + memberBToken = var.memberBToken + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + volume_type = var.volume_type +} diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster-master/output.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/output.tf new file mode 100755 index 00000000..c1f47385 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/output.tf @@ -0,0 +1,24 @@ +output "ami_id" { + value = module.launch_cluster_into_vpc.ami_id +} +output "cluster_public_ip" { + value = module.launch_cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.launch_cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.launch_cluster_into_vpc.member_b_public_ip +} +output "member_a_ssh" { + value = module.launch_cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.launch_cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.launch_cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.launch_cluster_into_vpc.member_b_url +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/terraform.tfvars new file mode 100755 index 00000000..28cb64a3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/terraform.tfvars @@ -0,0 +1,48 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster-master/variables.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/variables.tf new file mode 100755 index 00000000..d49cf50c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/variables.tf @@ -0,0 +1,183 @@ +// Module: Check Point CloudGuard Network Security Cross AZ Cluster into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1 \"us-east-1b\" = 2} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3 \"us-east-1b\" = 4} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster-master/versions.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/README.md b/deprecated/terraform/aws/R80.40/cross-az-cluster/README.md new file mode 100755 index 00000000..c070c984 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/README.md @@ -0,0 +1,196 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster into an existing VPC on AWS. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cross-az-cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cross-az-cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cross-az-cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_ids = ["subnet-abc123", "subnet-def456"] + private_subnet_ids = ["subnet-abc234", "subnet-def567"] + private_route_table = "rtb-12345678" + + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_ids | List of public subnet IDs to launch resources into. At least 2 | list(string) | n/a | n/a | yes | +| private_subnet_ids | List of private subnet IDs to launch resources into. At least 2 | list(string) | n/a | n/a | yes | | +| private_route_table | (Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX - R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------|--------------------------------------------------------------| +| ami_id | The ami id of the deployed Security Cross AZ Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240304 | Add x-chkp-cluster-ips, x-chkp-member-ips tags to cluster members | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221123 | R81.20 version support | +| 20221123 | Changed default version and added instances types | +| 20221123 | First release of Check Point Security Cross AZ Cluster Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../cross-az/LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_a_userdata.yaml b/deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_a_userdata.yaml new file mode 100755 index 00000000..1a3095e2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_a_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenA}\"" installationType=\"cross-az-cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"cross_az_cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" elasticIp=\"${MemberAPublicAddress}\" otherMemberIp=\"${MemberBPrivateAddressCluster}\" clusterIp=\"${PublicAddressCluster}\" secondaryIp=\"${MemberAPrivateAddressSecondary}\" otherMemberPrivateClusterIp=\"${MemberBPrivateAddressSecondary}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_b_userdata.yaml b/deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_b_userdata.yaml new file mode 100755 index 00000000..9ec9d23a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/cluster_member_b_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenB}\"" installationType=\"cross-az-cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"cross_az_cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" elasticIp=\"${MemberBPublicAddress}\" otherMemberIp=\"${MemberAPrivateAddressCluster}\" clusterIp=\"${PublicAddressCluster}\" secondaryIp=\"${MemberBPrivateAddressSecondary}\" otherMemberPrivateClusterIp=\"${MemberAPrivateAddressSecondary}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/locals.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster/locals.tf new file mode 100755 index 00000000..19f67f30 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/locals.tf @@ -0,0 +1,75 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + create_iam_role = var.predefined_role == "" ? 1 : 0 + provided_roue_table = var.private_route_table == "" ? 0 : 1 + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + //TokenA: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenA = split(" ", var.memberAToken) + tokenA_decode = base64decode(element(local.split_tokenA, length(local.split_tokenA)-1)) + regex_tokenA = regex(local.regex_token_valid, local.tokenA_decode) == local.tokenA_decode ? 0 : "Smart-1 Cloud token A is invalid format" + + //TokenB: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenB = split(" ", var.memberBToken) + tokenB_decode = base64decode(element(local.split_tokenB, length(local.split_tokenB)-1)) + regex_tokenB = regex(local.regex_token_valid, local.tokenB_decode) == local.tokenB_decode ? 0 : "Smart-1 Cloud token B is invalid format" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64=base64encode(var.gateway_SICKey) + gateway_password_hash_base64=base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/main.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster/main.tf new file mode 100755 index 00000000..d6a3bda3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/main.tf @@ -0,0 +1,294 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +resource "aws_iam_instance_profile" "cluster_instance_profile" { + path = "/" + role = local.create_iam_role == 1 ? join("", module.cluster_iam_role.*.cluster_iam_role_name) : var.predefined_role +} + +module "cluster_iam_role" { + source = "../modules/cluster-iam-role" + count = local.create_iam_role +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_instance_profile.cluster_instance_profile.role + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name +} + +resource "aws_network_interface" "member_a_external_eni" { + subnet_id = var.public_subnet_ids[0] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A external" + source_dest_check = false + private_ips_count = 1 + tags = { + x-chkp-interface-type = "external" } +} + +resource "aws_network_interface" "member_b_external_eni" { + subnet_id = var.public_subnet_ids[1] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B external" + source_dest_check = false + private_ips_count = 1 + tags = { + x-chkp-interface-type = "external" } +} + +resource "aws_network_interface" "member_a_internal_eni" { + subnet_id = var.private_subnet_ids[0] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A internal" + source_dest_check = false + tags = { + x-chkp-interface-type = "internal" } +} + +resource "aws_network_interface" "member_b_internal_eni" { + subnet_id = var.private_subnet_ids[1] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B internal" + source_dest_check = false + tags = { + x-chkp-interface-type = "internal" } +} + +resource "aws_route" "internal_default_route" { + count = local.internal_route_table_condition + route_table_id = var.private_route_table + lifecycle { + ignore_changes = [network_interface_id,] + } + destination_cidr_block = "0.0.0.0/0" + network_interface_id = aws_network_interface.member_a_internal_eni.id +} + +resource "aws_route_table_association" "private_rtb_a" { + count = var.private_route_table == "" ? 0 : 1 + route_table_id = var.private_route_table + subnet_id = var.private_subnet_ids[0] +} +resource "aws_route_table_association" "private_rtb_b" { + count = var.private_route_table == "" ? 0 : 1 + route_table_id = var.private_route_table + subnet_id = var.private_subnet_ids[1] +} + +resource "aws_launch_template" "member_a_launch_template" { + depends_on = [ + aws_network_interface.member_a_external_eni, + aws_network_interface.member_a_internal_eni + ] + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_a_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_a_internal_eni.id + device_index = 1 + } +} + +resource "aws_launch_template" "member_b_launch_template" { + depends_on = [ + aws_network_interface.member_b_external_eni, + aws_network_interface.member_b_internal_eni + ] + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_b_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_b_internal_eni.id + device_index = 1 + } +} + +resource "aws_instance" "member-a-instance" { + depends_on = [ + aws_launch_template.member_a_launch_template + ] + + launch_template { + id = aws_launch_template.member_a_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-A",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + aws_eip.member_a_eip.public_ip, aws_network_interface.member_a_external_eni.private_ip,aws_network_interface.member_a_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:secondary-external-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_a_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenA = var.memberAToken, + MemberAPublicAddress = aws_eip.member_a_eip.public_ip, + PublicAddressCluster = aws_eip.cluster_eip.public_ip, + MemberAPrivateAddressSecondary = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : "",//extracting member's secondary ip which represent the cluster ip + MemberBPrivateAddressCluster = aws_network_interface.member_b_internal_eni.private_ip, + MemberBPrivateAddressSecondary = length(tolist(aws_network_interface.member_b_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_b_external_eni.private_ips), [aws_network_interface.member_b_external_eni.private_ip])), 0) : "", + AllocateAddress = true, + OsVersion = local.version_split + }) +} + +resource "aws_instance" "member-b-instance" { + depends_on = [ + aws_launch_template.member_b_launch_template + ] + + launch_template { + id = aws_launch_template.member_b_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-B",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + aws_eip.member_b_eip.public_ip, aws_network_interface.member_b_external_eni.private_ip,aws_network_interface.member_b_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:secondary-external-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_b_external_eni.private_ips), [aws_network_interface.member_b_external_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_b_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenB = var.memberBToken, + MemberBPublicAddress = aws_eip.member_b_eip.public_ip, + PublicAddressCluster=aws_eip.cluster_eip.public_ip, + MemberBPrivateAddressSecondary = length(tolist(aws_network_interface.member_b_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_b_external_eni.private_ips), [aws_network_interface.member_b_external_eni.private_ip])), 0) : "", //extracting member's secondary ip which represent the member ip + MemberAPrivateAddressCluster=aws_network_interface.member_a_internal_eni.private_ip, + MemberAPrivateAddressSecondary = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : "", + AllocateAddress = true, + OsVersion = local.version_split + }) +} + +resource "aws_eip" "cluster_eip" { +} +resource "aws_eip" "member_a_eip" { +} +resource "aws_eip" "member_b_eip" { +} + +resource "aws_eip_association" "cluster_address_assoc" { + depends_on = [aws_instance.member-a-instance] + allocation_id = aws_eip.cluster_eip.id + lifecycle { + ignore_changes = [ + network_interface_id, private_ip_address + ] + } + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : ""//extracting member's secondary ip which represent the cluster ip +} +resource "aws_eip_association" "member_a_address_assoc" { + depends_on = [aws_instance.member-a-instance] + allocation_id = aws_eip.member_a_eip.id + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = aws_network_interface.member_a_external_eni.private_ip //primary +} +resource "aws_eip_association" "member_b_address_assoc" { + depends_on = [aws_instance.member-b-instance] + allocation_id = aws_eip.member_b_eip.id + network_interface_id = aws_network_interface.member_b_external_eni.id + private_ip_address = aws_network_interface.member_b_external_eni.private_ip //primary +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/output.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster/output.tf new file mode 100755 index 00000000..e475a650 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/output.tf @@ -0,0 +1,30 @@ +output "ami_id" { + value = module.amis.ami_id +} +output "cluster_public_ip" { + value = aws_eip.cluster_eip.*.public_ip +} +output "member_a_public_ip" { + value = aws_eip.member_a_eip.*.public_ip +} +output "member_b_public_ip" { + value = aws_eip.member_b_eip.*.public_ip +} +output "member_a_eni" { + value = aws_network_interface.member_a_external_eni.id +} +output "member_a_ssh" { + value = format("ssh -i %s admin@%s", var.key_name, aws_eip.member_a_eip.public_ip) +} +output "member_b_ssh" { + value = format("ssh -i %s admin@%s", var.key_name, aws_eip.member_b_eip.public_ip) +} +output "member_a_url" { + value = format("https://%s", aws_eip.member_a_eip.public_ip) +} +output "member_b_url" { + value = format("https://%s", aws_eip.member_b_eip.public_ip) +} +output "member_b_eni" { + value = aws_network_interface.member_b_external_eni.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/terraform.tfvars b/deprecated/terraform/aws/R80.40/cross-az-cluster/terraform.tfvars new file mode 100755 index 00000000..8c6aff9b --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/terraform.tfvars @@ -0,0 +1,42 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_ids = ["subnet-abc123", "subnet-def456"] +private_subnet_ids = ["subnet-abc234", "subnet-def567"] +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/variables.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster/variables.tf new file mode 100755 index 00000000..c2d66839 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/variables.tf @@ -0,0 +1,181 @@ +// Module: Check Point CloudGuard Network Security Cross AZ Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. At least 2" +} +variable "private_subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. At least 2" +} +variable "private_route_table" { + type = string + description = "(Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R80.40/cross-az-cluster/versions.tf b/deprecated/terraform/aws/R80.40/cross-az-cluster/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/cross-az-cluster/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/gateway-master/README.md b/deprecated/terraform/aws/R80.40/gateway-master/README.md new file mode 100755 index 00000000..26913346 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway-master/README.md @@ -0,0 +1,216 @@ +# Check Point CloudGuard Network Security Gateway Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation + + +See the [Automatically Provision a CloudGuard Security Gateway in AWS](https://supportcenter.us.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk131434) for additional information + +This solution uses the following modules: +- /terraform/aws/gateway +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/gateway-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/gateway: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/gateway: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + + +## Usage +- Fill all variables in the /terraform/aws/gateway-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/gateway-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + } + private_subnets_map = { + "us-east-1a" = 2 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Gateway-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + // --- Quick connect to Smart-1 Cloud (Recommended) --- + gateway_TokenKey = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + + // --- (Optional) Automatic Provisioning with Security Management Server Settings --- + control_gateway_over_public_or_private_address = "private" + management_server = "" + configuration_template = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Gateway instance: + ``` + allocate_and_associate_eip = true + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instance | string | n/a | Check-Point-Gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Security Gateway EC2 Instance | map(string) | n/a | {} | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_TokenKey | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| gateway_hostname | (Optional) Security Gateway prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| control_gateway_over_public_or_private_address | Determines if the Security Gateway is provisioned using its private or public address | string | - public
- private | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | "" | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | "" | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|------------------------------|----------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| internal_rt_id | The internal route table id | +| vpc_public_subnets_ids_list | A list of the public subnets ids | +| vpc_private_subnets_ids_list | A list of the private subnets ids | +| ami_id | The ami id of the deployed Security Gateway | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group id name | +| gateway_url | URL to the portal of the deployed Security Gateway | +| gateway_public_ip | The deployed Security Gateway Server AWS public ip | +| gateway_instance_id | The deployed Security Gateway AWS instance id | +| gateway_instance_name | The deployed Security Gateway AWS instance name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Gateway Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway-master/locals.tf b/deprecated/terraform/aws/R80.40/gateway-master/locals.tf new file mode 100755 index 00000000..0ca4134f --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway-master/locals.tf @@ -0,0 +1,48 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters." + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SICKey] must be at least 8 alphanumeric characters" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway-master/main.tf b/deprecated/terraform/aws/R80.40/gateway-master/main.tf new file mode 100755 index 00000000..dd09ebb4 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway-master/main.tf @@ -0,0 +1,66 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} + +module "launch_gateway_into_vpc" { + source = "../gateway" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_id = module.launch_vpc.public_subnets_ids_list[0] + private_subnet_id = module.launch_vpc.private_subnets_ids_list[0] + private_route_table = aws_route_table.private_subnet_rtb.id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_TokenKey = var.gateway_TokenKey + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + control_gateway_over_public_or_private_address = var.control_gateway_over_public_or_private_address + management_server = var.management_server + configuration_template = var.configuration_template +} diff --git a/deprecated/terraform/aws/R80.40/gateway-master/output.tf b/deprecated/terraform/aws/R80.40/gateway-master/output.tf new file mode 100755 index 00000000..2d8a716c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway-master/output.tf @@ -0,0 +1,33 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "internal_rtb_id" { + value = aws_route_table.private_subnet_rtb.id +} +output "vpc_public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "vpc_private_subnets_ids_list" { + value = module.launch_vpc.private_subnets_ids_list +} +output "ami_id" { + value = module.launch_gateway_into_vpc.ami_id +} +output "permissive_sg_id" { + value = module.launch_gateway_into_vpc.permissive_sg_id +} +output "permissive_sg_name" { + value = module.launch_gateway_into_vpc.permissive_sg_name +} +output "gateway_url" { + value = module.launch_gateway_into_vpc.gateway_url +} +output "gateway_public_ip" { + value = module.launch_gateway_into_vpc.gateway_public_ip +} +output "gateway_instance_id" { + value = module.launch_gateway_into_vpc.gateway_instance_id +} +output "gateway_instance_name" { + value = module.launch_gateway_into_vpc.gateway_instance_name +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/gateway-master/terraform.tfvars new file mode 100755 index 00000000..a8eb1d58 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway-master/terraform.tfvars @@ -0,0 +1,50 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 +} +private_subnets_map = { + "us-east-1a" = 2 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" + +// --- (Optional) Automatic Provisioning with Security Management Server Settings --- +control_gateway_over_public_or_private_address = "private" +management_server = "" +configuration_template = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway-master/variables.tf b/deprecated/terraform/aws/R80.40/gateway-master/variables.tf new file mode 100755 index 00000000..1c00c4f3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway-master/variables.tf @@ -0,0 +1,195 @@ +// Module: Check Point CloudGuard Network Security Gateway into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20." +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instance" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateway" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) Security Gateway prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} + +// --- (Optional) Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the Security Gateway is provisioned using its private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway-master/versions.tf b/deprecated/terraform/aws/R80.40/gateway-master/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/gateway/README.md b/deprecated/terraform/aws/R80.40/gateway/README.md new file mode 100755 index 00000000..b6cb4edc --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway/README.md @@ -0,0 +1,191 @@ +# Check Point CloudGuard Network Security Gateway Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation + +See the [Automatically Provision a CloudGuard Security Gateway in AWS](https://supportcenter.us.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk131434) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/gateway/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gateway/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/gateway/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_id = "subnet-123456" + private_subnet_id = "subnet-345678" + private_route_table = "rtb-12345678" + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Gateway-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + gateway_TokenKey = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + + // --- Automatic Provisioning with Security Management Server Settings (optional) --- + control_gateway_over_public_or_private_address = "private" + management_server = "" + configuration_template = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Gateway instance: + ``` + allocate_and_associate_eip = true + ``` + - To create route from '0.0.0.0/0' to the Security Gateway instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the security gateway | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the security gateway | string | n/a | n/a | yes | +| private_route_table | Sets '0.0.0.0/0' route to the Gateway instance in the specified route table (e.g. rtb-12a34567) | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instance | string | n/a | Check-Point-Gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Security Gateway EC2 Instance | map(string) | n/a | {} | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_TokenKey | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| gateway_hostname | (Optional) Security Gateway prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| control_gateway_over_public_or_private_address | Determines if the Security Gateway is provisioned using its private or public address | string | - public
- private | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | "" | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | "" | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|-----------------------|----------------------------------------------------| +| ami_id | The ami id of the deployed Security Gateway | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group id name | +| gateway_url | URL to the portal of the deployed Security Gateway | +| gateway_public_ip | The deployed Security Gateway Server AWS public ip | +| gateway_instance_id | The deployed Security Gateway AWS instance id | +| gateway_instance_name | The deployed Security Gateway AWS instance name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Gateway Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway/locals.tf b/deprecated/terraform/aws/R80.40/gateway/locals.tf new file mode 100755 index 00000000..79c894db --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway/locals.tf @@ -0,0 +1,48 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + //will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_token = split(" ", var.gateway_TokenKey) + token_decode = base64decode(element(local.split_token, length(local.split_token)-1)) + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + regex_token = regex(local.regex_token_valid, local.token_decode) == local.token_decode ? 0 : "Smart-1 Cloud token is invalid format" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway/main.tf b/deprecated/terraform/aws/R80.40/gateway/main.tf new file mode 100755 index 00000000..164d6bf0 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway/main.tf @@ -0,0 +1,119 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +resource "aws_iam_instance_profile" "gateway_instance_profile" { + count = local.enable_cloudwatch_policy + path = "/" + role = aws_iam_role.gateway_iam_role[count.index].name +} + +resource "aws_iam_role" "gateway_iam_role" { + count = local.enable_cloudwatch_policy + assume_role_policy = data.aws_iam_policy_document.gateway_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "gateway_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + } +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_role.gateway_iam_role[count.index].name + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name +} + +resource "aws_network_interface" "public_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth0" + source_dest_check = false + tags = { + Name = format("%s-external-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} +resource "aws_network_interface" "private_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth1" + source_dest_check = false + tags = { + Name = format("%s-internal-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +module "common_eip" { + source = "../modules/common/elastic_ip" + depends_on = [ + module.common_gateway_instance + ] + + allocate_and_associate_eip = var.allocate_and_associate_eip + external_eni_id = aws_network_interface.public_eni.id + private_ip_address = aws_network_interface.public_eni.private_ip +} + +module "common_internal_default_route" { + source = "../modules/common/internal_default_route" + + private_route_table = var.private_route_table + internal_eni_id = aws_network_interface.private_eni.id +} + +module "common_gateway_instance" { + source = "../modules/common/gateway_instance" + + external_eni_id = aws_network_interface.public_eni.id + internal_eni_id = aws_network_interface.private_eni.id + gateway_name = var.gateway_name + management_server = var.management_server + configuration_template = var.configuration_template + control_gateway_over_public_or_private_address = var.control_gateway_over_public_or_private_address + volume_size = var.volume_size + volume_encryption = var.volume_encryption + gateway_version = module.amis.version_license_with_suffix + gateway_instance_type = var.gateway_instance_type + instance_tags = var.instance_tags + key_name = var.key_name + iam_instance_profile_id = (local.enable_cloudwatch_policy == 1 ? aws_iam_instance_profile.gateway_instance_profile[0].id : "") + ami_id = module.amis.ami_id + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_TokenKey = var.gateway_TokenKey + gateway_bootstrap_script = var.gateway_bootstrap_script + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway/output.tf b/deprecated/terraform/aws/R80.40/gateway/output.tf new file mode 100755 index 00000000..ab3c934f --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway/output.tf @@ -0,0 +1,21 @@ +output "ami_id" { + value = module.amis.ami_id +} +output "permissive_sg_id" { + value = module.common_permissive_sg.permissive_sg_id +} +output "permissive_sg_name" { + value = module.common_permissive_sg.permissive_sg_name +} +output "gateway_url" { + value = format("https://%s", module.common_eip.gateway_eip_public_ip[0]) +} +output "gateway_public_ip" { + value = module.common_eip.gateway_eip_public_ip +} +output "gateway_instance_id" { + value = module.common_gateway_instance.gateway_instance_id +} +output "gateway_instance_name" { + value = module.common_gateway_instance.gateway_instance_name +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway/terraform.tfvars b/deprecated/terraform/aws/R80.40/gateway/terraform.tfvars new file mode 100755 index 00000000..02b1f781 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway/terraform.tfvars @@ -0,0 +1,46 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_id = "subnet-123456" +private_subnet_id = "subnet-345678" +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" + +// --- Automatic Provisioning with Security Management Server Settings (optional) --- +control_gateway_over_public_or_private_address = "private" +management_server = "" +configuration_template = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway/variables.tf b/deprecated/terraform/aws/R80.40/gateway/variables.tf new file mode 100755 index 00000000..7d32ab1a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway/variables.tf @@ -0,0 +1,192 @@ +// Module: Check Point CloudGuard Network Security Gateway into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_id" { + type = string + description = "The public subnet of the security gateway" +} +variable "private_subnet_id" { + type = string + description = "The private subnet of the security gateway" +} +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Security Gateway instance in the specified route table (e.g. rtb-12a34567)" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instance" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateway" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Security Gateway EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) Security Gateway prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} + +// --- (Optional) Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the Security Gateway is provisioned using its private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gateway/versions.tf b/deprecated/terraform/aws/R80.40/gateway/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gateway/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/gwlb-master/README.md b/deprecated/terraform/aws/R80.40/gwlb-master/README.md new file mode 100755 index 00000000..5d5957e6 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb-master/README.md @@ -0,0 +1,235 @@ +# Check Point CloudGuard Network Gateway Load Balancer Master Terraform module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [VPC](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/vpc) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` + - Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + + // --- Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + subnets_bit_length = 8 + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb1" + target_group_name = "tg1" + connection_acceptance_required = "false" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "" + gateways_addresses = "" + + // --- Other parameters --- + volume_type = "gp3" + + + ``` + +- Conditional creation + - To enable cloudwatch for gwlb-master: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-configuration | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb1 | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1 | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | Check-Point-GW-tf | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R80.40-BYOL
- R80.40-PAYG
- R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG | R81.20-BYOL | no | +| management_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | ""| no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | ""| no | + + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | Change default shell for the admin user to /etc/cli.sh | +| 20221215 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point CloudGuard Network Gateway Load Balancer master module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/gwlb-master/locals.tf b/deprecated/terraform/aws/R80.40/gwlb-master/locals.tf new file mode 100755 index 00000000..29a557ee --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb-master/locals.tf @@ -0,0 +1,61 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) + +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gwlb-master/main.tf b/deprecated/terraform/aws/R80.40/gwlb-master/main.tf new file mode 100755 index 00000000..da8bf39c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb-master/main.tf @@ -0,0 +1,69 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = {} + subnets_bit_length = var.subnets_bit_length +} + +module "gwlb" { + source = "../gwlb" + providers = { + aws = aws + } + vpc_id = module.launch_vpc.vpc_id + subnet_ids = module.launch_vpc.public_subnets_ids_list + + // --- General Settings --- + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + volume_size = var.volume_size + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + management_server = var.management_server + configuration_template = var.configuration_template + admin_shell = var.admin_shell + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = var.gateway_load_balancer_name + target_group_name = var.target_group_name + connection_acceptance_required = false + enable_cross_zone_load_balancing = var.enable_cross_zone_load_balancing + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateway_management = var.gateway_management + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + + volume_type = var.volume_type +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gwlb-master/output.tf b/deprecated/terraform/aws/R80.40/gwlb-master/output.tf new file mode 100755 index 00000000..15cb48a3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb-master/output.tf @@ -0,0 +1,24 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "management_public_ip" { + depends_on = [module.gwlb] + value = module.gwlb[*].management_public_ip +} +output "gwlb_arn" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_arn +} +output "gwlb_service_name" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_service_name +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gwlb-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/gwlb-master/terraform.tfvars new file mode 100755 index 00000000..f0f13c92 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb-master/terraform.tfvars @@ -0,0 +1,56 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +subnets_bit_length = 8 + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +connection_acceptance_required = "false" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R80.40/gwlb-master/variables.tf b/deprecated/terraform/aws/R80.40/gwlb-master/variables.tf new file mode 100755 index 00000000..fd72c46c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb-master/variables.tf @@ -0,0 +1,274 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "number_of_AZs" { + type = number + description = "Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter" + default = 2 +} +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "connection_acceptance_required" { + type = bool + description = "Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required)." + default = false +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Other parameters --- +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gwlb-master/versions.tf b/deprecated/terraform/aws/R80.40/gwlb-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/gwlb/README.md b/deprecated/terraform/aws/R80.40/gwlb/README.md new file mode 100755 index 00000000..a5f990ce --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb/README.md @@ -0,0 +1,228 @@ +# Check Point CloudGuard Network Gateway Load Balancer Terraform module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345" + subnet_ids = ["subnet-123457", "subnet-123456"] + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb1" + target_group_name = "tg1" + connection_acceptance_required = "false" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "" + gateways_addresses = "" + + // --- Other parameters --- + volume_type = "gp3" + + + ``` + +- Conditional creation + - To enable cloudwatch for GWLB: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| subnet_ids | The VPC subnets ID | string | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-configuration | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb1 | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1 | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | Check-Point-GW-tf | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R80.40-BYOL
- R80.40-PAYG
- R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231022 | Fixed template to populate x-chkp-tags correctly | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | Change default shell for the admin user to /etc/cli.sh | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220523 | Add support for cross zone load balancing | +| 20220414 | First release of Check Point CloudGuard Network Gateway Load Balancer module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/gwlb/locals.tf b/deprecated/terraform/aws/R80.40/gwlb/locals.tf new file mode 100755 index 00000000..44363311 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb/locals.tf @@ -0,0 +1,55 @@ +locals { + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gwlb/main.tf b/deprecated/terraform/aws/R80.40/gwlb/main.tf new file mode 100755 index 00000000..7c4e4616 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb/main.tf @@ -0,0 +1,99 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +module "gateway_load_balancer" { + source = "../modules/common/load_balancer" + + load_balancers_type = "gateway" + instances_subnets = var.subnet_ids + prefix_name = var.gateway_load_balancer_name + internal = true + + security_groups = [] + tags = { + x-chkp-management = var.management_server + x-chkp-template = var.configuration_template + } + vpc_id = var.vpc_id + load_balancer_protocol = "GENEVE" + target_group_port = 6081 + listener_port = 6081 + cross_zone_load_balancing = var.enable_cross_zone_load_balancing +} + +resource "aws_vpc_endpoint_service" "gwlb_endpoint_service" { +depends_on = [module.gateway_load_balancer] + gateway_load_balancer_arns = module.gateway_load_balancer[*].load_balancer_arn + acceptance_required = var.connection_acceptance_required + + tags = { + "Name" = "gwlb-endpoint-service-${var.gateway_load_balancer_name}" + } +} + +module "autoscale_gwlb" { + source = "../autoscale-gwlb" + providers = { + aws = aws + } + depends_on = [module.gateway_load_balancer] + + target_groups = module.gateway_load_balancer[*].target_group_arn + vpc_id = var.vpc_id + subnet_ids = var.subnet_ids + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + metadata_imdsv2_required = var.metadata_imdsv2_required + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + admin_shell = var.admin_shell + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + management_server = var.management_server + configuration_template = var.configuration_template + volume_type = var.volume_type +} + +data "aws_region" "current"{} + +module "management" { + providers = { + aws = aws + } + count = local.deploy_management_condition ? 1 : 0 + source = "../management" + + vpc_id = var.vpc_id + subnet_id = var.subnet_ids[0] + management_name = var.management_server + management_instance_type = var.management_instance_type + key_name = var.key_name + allocate_and_associate_eip = true + volume_encryption = var.enable_volume_encryption ? "alias/aws/ebs" : "" + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + allow_upload_download = var.allow_upload_download + admin_cidr = var.admin_cidr + admin_shell = var.admin_shell + gateway_addresses = var.gateways_addresses + gateway_management = var.gateway_management + management_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"management_gwlb\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; autoprov_cfg -f init AWS -mn ${var.management_server} -tn ${var.configuration_template} -cn gwlb-controller -po ${var.gateways_policy} -otp ${var.gateway_SICKey} -r ${data.aws_region.current.name} -ver ${split("-", var.gateway_version)[0]} -iam; echo -e '\nFinished Bootstrap script\n'" + volume_type = var.volume_type + is_gwlb_iam = true +} diff --git a/deprecated/terraform/aws/R80.40/gwlb/output.tf b/deprecated/terraform/aws/R80.40/gwlb/output.tf new file mode 100755 index 00000000..3beba7ee --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb/output.tf @@ -0,0 +1,22 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "gwlb_arn" { + value = module.gateway_load_balancer.load_balancer_arn +} +output "gwlb_service_name" { + value = "com.amazonaws.vpce.${data.aws_region.current.name}.${aws_vpc_endpoint_service.gwlb_endpoint_service.id}" +} +output "management_public_ip" { + depends_on = [module.management] + value = module.management[*].management_public_ip +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gwlb/terraform.tfvars b/deprecated/terraform/aws/R80.40/gwlb/terraform.tfvars new file mode 100755 index 00000000..0e26ad11 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb/terraform.tfvars @@ -0,0 +1,52 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_ids = ["subnet-123456", "subnet-345678"] + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +connection_acceptance_required = "false" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R80.40/gwlb/variables.tf b/deprecated/terraform/aws/R80.40/gwlb/variables.tf new file mode 100755 index 00000000..5f099c6c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb/variables.tf @@ -0,0 +1,263 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. Recommended at least 2" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "connection_acceptance_required" { + type = bool + description = "Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required)." + default = false +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Other parameters --- +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/gwlb/versions.tf b/deprecated/terraform/aws/R80.40/gwlb/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/gwlb/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/management/README.md b/deprecated/terraform/aws/R80.40/management/README.md new file mode 100755 index 00000000..0acbdd0a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/README.md @@ -0,0 +1,200 @@ +# Check Point CloudGuard Network Security Management Server Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Management Server into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Security Management Server with CloudGuard for AWS](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk130372) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/management/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/management/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/management/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_id = "subnet-abc123" + + // --- EC2 Instances Configuration --- + management_name = "CP-Management-tf" + management_instance_type = "m5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- IAM Permissions --- + iam_permissions = "Create with read permissions" + predefined_role = "" + sts_roles = [] + + // --- Check Point Settings --- + management_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + // --- Security Management Server Settings --- + management_hostname = "mgmt-tf" + management_installation_type = "Primary management" + SICKey = "" + allow_upload_download = "true" + gateway_management = "Locally managed" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + primary_ntp = "" + secondary_ntp = "" + management_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Management instance: + ``` + allocate_and_associate_eip = true + ``` + - To create IAM Role: + ``` + iam_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_id | To access the instance from the internet, make sure the subnet has a route to the internet | string | n/a | n/a | yes | +| management_name | (Optional) The name tag of the Security Management instance | string | n/a | Check-Point-Management-tf | no | +| management_instance_type | The instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Management EC2 Instance | map(string) | n/a | {} | no | +| iam_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| predefined_role | (Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing' | string | n/a | "" | no | +| sts_roles | (Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing' | list(string) | n/a | [] | no | +| management_version | Management version and license | string | - R80.40-BYOL
- R80.40-PAYG
- R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| management_password_hash | (Optional) Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) | string | n/a | "" | no | +| management_hostname | (Optional) Security Management Server prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| management_installation_type | Determines if this is the primary management server, secondary management server or log server | string | - Primary management
- Secondary management
- Log Server
| Primary management | yes | +| SICKey | Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Security Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| management_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|--------------------------------------------------------------| +| management_instance_id | The deployed Security Management Server AWS instance id | +| management_instance_name | The deployed Security Management AWS instance name | +| management_instance_tags | The deployed Security Management Server AWS tags | +| management_public_ip | The deployed Security Management Server AWS public ip | +| management_url | URL to the portal of the deployed Security Management Server | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240207 | Added Log Server installation support | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Security Management Server Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/management/locals.tf b/deprecated/terraform/aws/R80.40/management/locals.tf new file mode 100755 index 00000000..896719ba --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/locals.tf @@ -0,0 +1,76 @@ +locals { + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.iam_permissions) + + use_role = var.iam_permissions == "None (configure later)" ? 0 : 1 + create_iam_role = var.iam_permissions == "Create with assume role permissions (specify an STS role ARN)" || var.iam_permissions == "Create with read permissions" || var.iam_permissions == "Create with read-write permissions" + pre_role = (local.use_role == 1 && local.create_iam_role == false) ? 1 : 0 + new_instance_profile = (local.create_iam_role == true && local.use_role == 1) ? 1 : 0 + + new_instance_profile_general = local.new_instance_profile == 1 && var.is_gwlb_iam == false ? 1 : 0 + new_instance_profile_gwlb = local.new_instance_profile == 1 && var.is_gwlb_iam ? 1 : 0 + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // Will fail if var.gateway_management is invalid + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + regex_valid_sic_key = "(|[a-zA-Z0-9]{8,})" + // Will fail if var.SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.SICKey) == var.SICKey ? 0 : "Variable [SICKey] must be at least 8 alphanumeric characters" + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.management_version), 0) + + management_bootstrap_script64 = base64encode(var.management_bootstrap_script) + management_SICkey_base64=base64encode(var.SICKey) + management_password_hash_base64=base64encode(var.management_password_hash) + maintenance_mode_password_hash_base64=base64encode(var.management_maintenance_mode_password_hash) + + manage_over_the_internet = var.gateway_management == "Over the internet" ? true : false + manage_over_internet_and_EIP = var.allocate_and_associate_eip && local.manage_over_the_internet ? true : false + pub_mgmt = local.manage_over_internet_and_EIP ? true : false + + management_installation_type_allowed_values = [ + "Primary management", + "Secondary management", + "Log Server"] + validate_management_installation_type = index(local.management_installation_type_allowed_values, var.management_installation_type) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/management/main.tf b/deprecated/terraform/aws/R80.40/management/main.tf new file mode 100755 index 00000000..3714dfa2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/main.tf @@ -0,0 +1,221 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.management_version + chkp_type = "management" +} + +resource "aws_security_group" "management_sg" { + description = "terraform Management security group" + vpc_id = var.vpc_id + name_prefix = format("%s_SecurityGroup", var.management_name) + // Group name + tags = { + Name = format("%s_SecurityGroup", var.management_name) + // Resource name + } + ingress { + from_port = 257 + to_port = 257 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18191 + to_port = 18191 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18192 + to_port = 18192 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18208 + to_port = 18208 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18210 + to_port = 18210 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18211 + to_port = 18211 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18221 + to_port = 18221 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18264 + to_port = 18264 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + + ingress { + from_port = 22 + to_port = 22 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 443 + to_port = 443 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 18190 + to_port = 18190 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 19009 + to_port = 19009 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } +} + +resource "aws_network_interface" "external-eni" { + subnet_id = var.subnet_id + security_groups = [aws_security_group.management_sg.id] + description = "eth0" + source_dest_check = true + tags = { + Name = format("%s-network_interface", var.management_name) + } +} + +resource "aws_eip" "eip" { + count = var.allocate_and_associate_eip ? 1 : 0 + network_interface = aws_network_interface.external-eni.id +} + +resource "aws_iam_instance_profile" "management_instance_profile" { + count = local.pre_role + path = "/" + role = var.predefined_role +} + +resource "aws_launch_template" "management_launch_template" { + depends_on = [ + aws_network_interface.external-eni, + aws_eip.eip + ] + + instance_type = var.management_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = local.use_role == 1 ? (local.pre_role == 1 ? aws_iam_instance_profile.management_instance_profile[0].id : join("", (var.is_gwlb_iam == true ? module.cme_iam_role_gwlb.*.cme_iam_profile_name : module.cme_iam_role.*.cme_iam_profile_name))): "" + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.external-eni.id + device_index = 0 + } +} + +resource "aws_instance" "management-instance" { + depends_on = [ + aws_launch_template.management_launch_template + ] + + launch_template { + id = aws_launch_template.management_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.management_name + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = var.volume_type + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/management_userdata.yaml", { + // script's arguments + Hostname = var.management_hostname, + PasswordHash = local.management_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + NTPPrimary = var.primary_ntp + NTPSecondary = var.secondary_ntp + Shell = var.admin_shell, + AdminSubnet = var.admin_cidr + ManagementInstallationType = var.management_installation_type + SICKey = local.management_SICkey_base64, + OsVersion = local.version_split + EnableInstanceConnect = var.enable_instance_connect + AllocateElasticIP = var.allocate_and_associate_eip + GatewayManagement = var.gateway_management + BootstrapScript = local.management_bootstrap_script64 + PubMgmt = local.pub_mgmt + + }) +} + +module "cme_iam_role" { + source = "../cme-iam-role" + providers = { + aws = aws + } + count = local.new_instance_profile_general + + sts_roles = var.sts_roles + permissions = var.iam_permissions +} + +module "cme_iam_role_gwlb" { + source = "../cme-iam-role-gwlb" + providers = { + aws = aws + } + count = local.new_instance_profile_gwlb + + sts_roles = var.sts_roles + permissions = var.iam_permissions +} diff --git a/deprecated/terraform/aws/R80.40/management/management_userdata.yaml b/deprecated/terraform/aws/R80.40/management/management_userdata.yaml new file mode 100755 index 00000000..0f3801ff --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/management_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py sicKey=\"${SICKey}\" installationType=\"management\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"management\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" "management_installation_type=\"${ManagementInstallationType}\"" adminSubnet=\"${AdminSubnet}\" allocatePublicAddress=\"${AllocateElasticIP}\" overTheInternet=\"${PubMgmt}\" bootstrapScript64=\"${BootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/management/output.tf b/deprecated/terraform/aws/R80.40/management/output.tf new file mode 100755 index 00000000..da20727b --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/output.tf @@ -0,0 +1,19 @@ +output "Deployment" { + value = "Finalizing configuration may take up to 20 minutes after deployment is finished." +} + +output "management_instance_id" { + value = aws_instance.management-instance.id +} +output "management_instance_name" { + value = aws_instance.management-instance.tags["Name"] +} +output "management_instance_tags" { + value = aws_instance.management-instance.tags +} +output "management_public_ip" { + value = aws_instance.management-instance.public_ip +} +output "management_url" { + value = format("https://%s", aws_instance.management-instance.public_ip) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/management/terraform.tfvars b/deprecated/terraform/aws/R80.40/management/terraform.tfvars new file mode 100755 index 00000000..81891681 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/terraform.tfvars @@ -0,0 +1,42 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_id = "subnet-abc123" + +// --- EC2 Instances Configuration --- +management_name = "CP-Management-tf" +management_instance_type = "m5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- IAM Permissions --- +iam_permissions = "Create with read permissions" +predefined_role = "" +sts_roles = [] + +// --- Check Point Settings --- +management_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +// --- Security Management Server Settings --- +management_hostname = "mgmt-tf" +management_installation_type = "Primary management" +SICKey = "" +allow_upload_download = "true" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "" +secondary_ntp = "" +management_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" diff --git a/deprecated/terraform/aws/R80.40/management/variables.tf b/deprecated/terraform/aws/R80.40/management/variables.tf new file mode 100755 index 00000000..763918f0 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/variables.tf @@ -0,0 +1,194 @@ +// Module: Check Point CloudGuard Network Security Management Server into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_id" { + type = string + description = "To access the instance from the internet, make sure the subnet has a route to the internet" +} + +// --- EC2 Instance Configuration --- +variable "management_name" { + type = string + description = "(Optional) The name tag of the Security Management instance" + default = "Check-Point-Management-tf" +} +variable "management_instance_type" { + type = string + description = "The instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable AWS Instance Connect - Ec2 Instance Connect is not supported with versions prior to R80.40" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Management EC2 Instance" + default = {} +} + +// --- IAM Permissions (ignored when the installation is not Primary Management Server) --- +variable "iam_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read permissions" +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing'" + default = "" +} +variable "sts_roles" { + type = list(string) + description = "(Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing'" + default = [] +} + +// --- Check Point Settings --- +variable "management_version" { + type = string + description = "Management version and license" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Security Management Server Settings --- +variable "management_hostname" { + type = string + description = "(Optional) Security Management Server prompt hostname" + default = "" +} +variable "management_installation_type" { + type = string + description = "Determines the Management Server installation type: Primary management, Secondary management, Log Server" + default = "Primary management" +} +variable "SICKey" { + type = string + description = "Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Security Management Server" + default = "0.0.0.0/0" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "management_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "is_gwlb_iam" { + type = bool + default = false +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/management/versions.tf b/deprecated/terraform/aws/R80.40/management/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/management/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/mds/README.md b/deprecated/terraform/aws/R80.40/mds/README.md new file mode 100755 index 00000000..112c8958 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/README.md @@ -0,0 +1,190 @@ +# Check Point CloudGuard Network Multi-Domain Server Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Multi-Domain Server into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Multi-Domain Management Deployment on AWS](https://supportcenter.us.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk143213) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/mds/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/mds/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/mds/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_id = "subnet-abc123" + + // --- EC2 Instances Configuration --- + mds_name = "CP-MDS-tf" + mds_instance_type = "m5.12xlarge" + key_name = "publickey" + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- IAM Permissions --- + iam_permissions = "Create with read permissions" + predefined_role = "" + sts_roles = [] + + // --- Check Point Settings --- + mds_version = "R81.20-BYOL" + mds_admin_shell = "/etc/cli.sh" + mds_password_hash = "" + mds_maintenance_mode_password_hash = "" + + // --- Multi-Domain Server Settings --- + mds_hostname = "mds-tf" + mds_SICKey = "" + allow_upload_download = "true" + mds_installation_type = "Primary Multi-Domain Server" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + primary_ntp = "" + secondary_ntp = "" + mds_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + ``` + +- Conditional creation + - To create IAM Role: + ``` + iam_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + and + mds_installation_type = "Primary Multi-Domain Server" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_id | To access the instance from the internet, make sure the subnet has a route to the internet | string | n/a | n/a | yes | +| mds_name | (Optional) The name tag of the Multi-Domain Server instance | string | n/a | Check-Point-MDS-tf | no | +| mds_instance_type | The instance type of the Multi-Domain Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.12xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Multi-Domain Server EC2 Instance | map(string) | n/a | {} | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| iam_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| predefined_role | (Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing' | string | n/a | "" | no | +| sts_roles | (Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing' | list(string) | n/a | [] | no | +| mds_version | Multi-Domain Server version and license | string | - R80.40-BYOL
- R81-BYOL
- R81.10-BYOL
- R81.20-BYOL
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| mds_admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| mds_password_hash | (Optional) Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) | string | n/a | "" | no | +| mds_hostname | (Optional) Multi-Domain Server prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| mds_SICKey | Mandatory if deploying a Secondary Multi-Domain Server or Multi-Domain Log Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| mds_installation_type | Determines the Multi-Domain Server installation type | string | - Primary Multi-Domain Server
- Secondary Multi-Domain Server
- Multi-Domain Log Server | Primary Multi-Domain Server | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Multi-Domain Server | string | valid CIDR | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Multi-Domain Server | string | valid CIDR | 0.0.0.0/0 | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| mds_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| mds_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|-------------------|----------------------------------------------------| +| mds_instance_id | The deployed Multi-Domain Server AWS instance id | +| mds_instance_name | The deployed Multi-Domain Server AWS instance name | +| mds_instance_tags | The deployed Multi-Domain Server AWS tags | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Multi-Domain Server Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/mds/locals.tf b/deprecated/terraform/aws/R80.40/mds/locals.tf new file mode 100755 index 00000000..7dd690a2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/locals.tf @@ -0,0 +1,69 @@ +locals { + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.iam_permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.iam_permissions) + + installation_type_allowed_values = [ + "Primary Multi-Domain Server", + "Secondary Multi-Domain Server", + "Multi-Domain Log Server"] + // Will fail if var.mds_installation_type is invalid + validate_installation_type = index(local.installation_type_allowed_values, var.mds_installation_type) + + primary_mds = var.mds_installation_type == "Primary Multi-Domain Server" + secondary_mds = var.mds_installation_type == "Secondary Multi-Domain Server" + + use_role = var.iam_permissions != "None (configure later)" && local.primary_mds ? 1 : 0 + create_iam_role = (local.primary_mds) && (var.iam_permissions == "Create with assume role permissions (specify an STS role ARN)" || var.iam_permissions == "Create with read permissions" || var.iam_permissions == "Create with read-write permissions") + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.mds_admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.mds_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.mds_hostname) == var.mds_hostname ? 0 : "Variable [mds_hostname] must be a valid hostname label or an empty string" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_mds_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.mds_password_hash is invalid + regex_mds_password_hash = regex(local.regex_valid_mds_password_hash, var.mds_password_hash) == var.mds_password_hash ? 0 : "Variable [mds_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_mds_password_hash, var.mds_maintenance_mode_password_hash) == var.mds_maintenance_mode_password_hash ? 0 : "Variable [mds_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_sic_key = "(|[a-zA-Z0-9]{8,})" + // Will fail if var.mds_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.mds_SICKey) == var.mds_SICKey ? 0 : "Variable [mds_SICKey] must be at least 8 alphanumeric characters" + //Splits the version and licence and returns the os version + version_split = element(split("-", var.mds_version), 0) + + mds_bootstrap_script64 = base64encode(var.mds_bootstrap_script) + mds_SICkey_base64 = base64encode(var.mds_SICKey) + mds_password_hash_base64 =base64encode(var.mds_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.mds_maintenance_mode_password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/mds/main.tf b/deprecated/terraform/aws/R80.40/mds/main.tf new file mode 100755 index 00000000..8a22b264 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/main.tf @@ -0,0 +1,194 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.mds_version + chkp_type = "mds" +} + +resource "aws_security_group" "mds_sg" { + description = "terraform Multi-Domain Server security group" + vpc_id = var.vpc_id + name_prefix = format("%s_SecurityGroup", var.mds_name) + // Group name + tags = { + Name = format("%s_SecurityGroup", var.mds_name) + // Resource name + } + ingress { + from_port = 257 + to_port = 257 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 8211 + to_port = 8211 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18191 + to_port = 18191 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18192 + to_port = 18192 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18208 + to_port = 18208 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18210 + to_port = 18210 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18211 + to_port = 18211 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18221 + to_port = 18221 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18264 + to_port = 18264 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 22 + to_port = 22 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 443 + to_port = 443 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 18190 + to_port = 18190 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 19009 + to_port = 19009 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } +} + +resource "aws_iam_instance_profile" "mds_instance_profile" { + count = local.use_role + path = "/" + role = local.create_iam_role ? join("", module.cme_iam_role.*.cme_iam_role_name) : var.predefined_role +} + +resource "aws_network_interface" "external-eni" { + subnet_id = var.subnet_id + security_groups = [aws_security_group.mds_sg.id] + description = "eth0" + source_dest_check = true + tags = { + Name = format("%s-network_interface", var.mds_name) + } +} + +resource "aws_launch_template" "mds_launch_template" { + instance_type = var.mds_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = local.use_role == 1 ? aws_iam_instance_profile.mds_instance_profile[0].id : "" + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.external-eni.id + device_index = 0 + } +} + +resource "aws_instance" "mds-instance" { + launch_template { + id = aws_launch_template.mds_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.mds_name + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + user_data = templatefile("${path.module}/mds_userdata.yaml", { + // script's arguments + Hostname = var.mds_hostname, + PasswordHash = local.mds_password_hash_base64 + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + AllowUploadDownload = var.allow_upload_download, + NTPPrimary = var.primary_ntp + NTPSecondary = var.secondary_ntp + Shell = var.mds_admin_shell, + AdminSubnet = var.admin_cidr + IsPrimary = local.primary_mds + IsSecondary = local.secondary_mds + SICKey = local.mds_SICkey_base64, + EnableInstanceConnect = var.enable_instance_connect + BootstrapScript = local.mds_bootstrap_script64 + OsVersion = local.version_split + }) +} + +module "cme_iam_role" { + source = "../cme-iam-role" + providers = { + aws = aws + } + count = local.create_iam_role ? 1 : 0 + + sts_roles = var.sts_roles + permissions = var.iam_permissions +} diff --git a/deprecated/terraform/aws/R80.40/mds/mds_userdata.yaml b/deprecated/terraform/aws/R80.40/mds/mds_userdata.yaml new file mode 100755 index 00000000..3321cd60 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/mds_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py sicKey=\"${SICKey}\" installationType=\"mds\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"mds\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" primary=\"${IsPrimary}\" secondary=\"${IsSecondary}\" adminSubnet=\"${AdminSubnet}\" bootstrapScript64=\"${BootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/mds/output.tf b/deprecated/terraform/aws/R80.40/mds/output.tf new file mode 100755 index 00000000..c1d3783a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/output.tf @@ -0,0 +1,13 @@ +output "Deployment" { + value = "Finalizing configuration may take up to 20 minutes after deployment is finished." +} + +output "mds_instance_id" { + value = aws_instance.mds-instance.id +} +output "mds_instance_name" { + value = aws_instance.mds-instance.tags["Name"] +} +output "mds_instance_tags" { + value = aws_instance.mds-instance.tags +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/mds/terraform.tfvars b/deprecated/terraform/aws/R80.40/mds/terraform.tfvars new file mode 100755 index 00000000..e79af359 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/terraform.tfvars @@ -0,0 +1,41 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_id = "subnet-abc123" + +// --- EC2 Instances Configuration --- +mds_name = "CP-MDS-tf" +mds_instance_type = "m5.12xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- IAM Permissions --- +iam_permissions = "Create with read permissions" +predefined_role = "" +sts_roles = [] + +// --- Check Point Settings --- +mds_version = "R81.20-BYOL" +mds_admin_shell = "/etc/cli.sh" +mds_password_hash = "" +mds_maintenance_mode_password_hash = "" + +// --- Multi-Domain Server Settings --- +mds_hostname = "mds-tf" +mds_SICKey = "" +allow_upload_download = "true" +mds_installation_type = "Primary Multi-Domain Server" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "" +secondary_ntp = "" +mds_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" diff --git a/deprecated/terraform/aws/R80.40/mds/variables.tf b/deprecated/terraform/aws/R80.40/mds/variables.tf new file mode 100755 index 00000000..f4218e4c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/variables.tf @@ -0,0 +1,175 @@ +// Module: Check Point CloudGuard Network Multi-Domain Server into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_id" { + type = string + description = "To access the instance from the internet, make sure the subnet has a route to the internet" +} + +// --- EC2 Instance Configuration --- +variable "mds_name" { + type = string + description = "(Optional) The name tag of the Multi-Domain Server instance" + default = "Check-Point-MDS-tf" +} +variable "mds_instance_type" { + type = string + description = "The instance type of the Multi-Domain Server" + default = "m5.2xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "mds" + instance_type = var.mds_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Multi-Domain Server EC2 Instance" + default = {} +} + +// --- IAM Permissions (ignored when the installation type is not Primary Multi-Domain Server) --- +variable "iam_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read permissions" +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing'" + default = "" +} +variable "sts_roles" { + type = list(string) + description = "(Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing'" + default = [] +} + +// --- Check Point Settings --- +variable "mds_version" { + type = string + description = "Multi-Domain Server version and license" + default = "R81.20-BYOL" +} +module "validate_mds_version" { + source = "../modules/common/version_license" + + chkp_type = "mds" + version_license = var.mds_version +} +variable "mds_admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "mds_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "mds_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Multi-Domain Server Settings --- +variable "mds_hostname" { + type = string + description = "(Optional) Multi-Domain Server prompt hostname" + default = "" +} +variable "mds_SICKey" { + type = string + description = "Mandatory if deploying a Secondary Multi-Domain Server or Multi-Domain Log Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "mds_installation_type" { + type = string + description = "Determines the Multi-Domain Server installation type" + default = "Primary Multi-Domain Server" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Multi-Domain Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Multi-Domain Server" + default = "0.0.0.0/0" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "mds_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} diff --git a/deprecated/terraform/aws/R80.40/mds/versions.tf b/deprecated/terraform/aws/R80.40/mds/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/mds/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/modules/amis/main.tf b/deprecated/terraform/aws/R80.40/modules/amis/main.tf new file mode 100755 index 00000000..355ed112 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/amis/main.tf @@ -0,0 +1,23 @@ +locals { + amis_yaml_regionMap = yamldecode(split("Resources", data.http.amis_yaml_http.response_body)[0]).Mappings.RegionMap + amis_yaml_converterMap = yamldecode(split("Resources", data.http.amis_yaml_http.response_body)[0]).Mappings.ConverterMap + + + // Variables example: + // version_license = "R80.40-PAYG-NGTX" + // RESULT: + // version_license_key = "R80.40-PAYG-NGTX-GW" + + // version_license_value = "R8040PAYGNGTXGW" + + version_license_key_mgmt_gw = format("%s%s", var.version_license, var.chkp_type == "gateway" ? "-GW" : var.chkp_type == "management"? "-MGMT" : var.chkp_type == "mds" ? "-MGMT" : "") + version_license_key = var.chkp_type == "standalone" ? format("%s%s", var.version_license, element(split("-", var.version_license), 1) == "BYOL" ? "-MGMT" : "") : local.version_license_key_mgmt_gw + + version_license_value = local.amis_yaml_converterMap[local.version_license_key]["Value"] + + // Variables example: + // region = "us-east-1" + // version_license_key - see above + // RESULT: local.ami_id = "ami-1234567" + ami_id = local.amis_yaml_regionMap[local.region][local.version_license_value] +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/amis/output.tf b/deprecated/terraform/aws/R80.40/modules/amis/output.tf new file mode 100755 index 00000000..0be16a15 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/amis/output.tf @@ -0,0 +1,6 @@ +output "ami_id" { + value = local.ami_id +} +output "version_license_with_suffix" { + value = local.version_license_key +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/amis/variables.tf b/deprecated/terraform/aws/R80.40/modules/amis/variables.tf new file mode 100755 index 00000000..3cbf7b1b --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/amis/variables.tf @@ -0,0 +1,26 @@ +variable "amis_url" { + type = string + description = "URL to amis.yaml" + default = "https://cgi-cfts-staging.s3.amazonaws.com/utils/amis.yaml" +} + +data "http" "amis_yaml_http" { + url = var.amis_url +} + +data "aws_region" "current" {} +locals { + region = data.aws_region.current.name +} + +// --- Version & License --- +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +variable "version_license" { + type = string + description = "Version and license" +} + diff --git a/deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/main.tf b/deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/main.tf new file mode 100755 index 00000000..3d191a01 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/main.tf @@ -0,0 +1,18 @@ +data "aws_iam_policy_document" "policy_document" { + version = "2012-10-17" + statement { + actions = ["cloudwatch:PutMetricData"] + effect = "Allow" + resources = ["*"] + } +} + +resource "aws_iam_policy" "policy" { + name_prefix = format("%s-iam_policy", var.tag_name) + policy = data.aws_iam_policy_document.policy_document.json +} + +resource "aws_iam_role_policy_attachment" "attachment" { + role = var.role + policy_arn = aws_iam_policy.policy.arn +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/variables.tf b/deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/variables.tf new file mode 100755 index 00000000..2d3f9452 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/cloudwatch-policy/variables.tf @@ -0,0 +1,9 @@ +variable "tag_name" { + type = string + description = "(Optional) IAM policy name prefix" + default = "cloudwatch" +} +variable "role" { + type = string + description = "A IAM role to attach the cloudwatch policy to it" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/cluster-iam-role/main.tf b/deprecated/terraform/aws/R80.40/modules/cluster-iam-role/main.tf new file mode 100755 index 00000000..b56eacd6 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/cluster-iam-role/main.tf @@ -0,0 +1,38 @@ +resource "aws_iam_role" "cluster_iam_role" { + assume_role_policy = data.aws_iam_policy_document.cluster_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "cluster_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + } +} + +data "aws_iam_policy_document" "cluster_role_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "ec2:AssignPrivateIpAddresses", + "ec2:AssociateAddress", + "ec2:CreateRoute", + "ec2:DescribeNetworkInterfaces", + "ec2:DescribeRouteTables", + "ec2:ReplaceRoute"] + resources = ["*"] + } +} +resource "aws_iam_policy" "cluster_role_policy" { + policy = data.aws_iam_policy_document.cluster_role_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_policy" { + policy_arn = aws_iam_policy.cluster_role_policy.arn + role = aws_iam_role.cluster_iam_role.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/cluster-iam-role/output.tf b/deprecated/terraform/aws/R80.40/modules/cluster-iam-role/output.tf new file mode 100755 index 00000000..7bbf0351 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/cluster-iam-role/output.tf @@ -0,0 +1,9 @@ +output "cluster_iam_role" { + value = aws_iam_role.cluster_iam_role +} +output "cluster_iam_role_arn" { + value = aws_iam_role.cluster_iam_role.arn +} +output "cluster_iam_role_name" { + value = aws_iam_role.cluster_iam_role.name +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/locals.tf b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/locals.tf new file mode 100755 index 00000000..c4af5bca --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/locals.tf @@ -0,0 +1,3 @@ +locals { + allocate_and_associate_eip_condition = var.allocate_and_associate_eip == true ? 1 : 0 +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/main.tf b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/main.tf new file mode 100755 index 00000000..879748a9 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/main.tf @@ -0,0 +1,10 @@ +resource "aws_eip" "gateway_eip" { + count = local.allocate_and_associate_eip_condition + network_interface = var.external_eni_id +} +resource "aws_eip_association" "address_assoc" { + count = local.allocate_and_associate_eip_condition + allocation_id = aws_eip.gateway_eip[count.index].id + network_interface_id = var.external_eni_id + private_ip_address = var.private_ip_address +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/output.tf b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/output.tf new file mode 100755 index 00000000..31857b83 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/output.tf @@ -0,0 +1,9 @@ +output "gateway_eip_id" { + value = aws_eip.gateway_eip.*.id +} +output "gateway_eip_public_ip" { + value = aws_eip.gateway_eip.*.public_ip +} +output "gateway_eip_attached_instance" { + value = aws_eip.gateway_eip.*.instance +} diff --git a/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/variables.tf b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/variables.tf new file mode 100755 index 00000000..c6881436 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/elastic_ip/variables.tf @@ -0,0 +1,13 @@ +variable "allocate_and_associate_eip" { + type = bool + description = "If set to TRUE, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "external_eni_id" { + type = string + description = "The external-eni of the security gateway" +} +variable "private_ip_address" { + type = string + description = "The primary or secondary private IP address to associate with the Elastic IP address. " +} diff --git a/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/gateway_userdata.yaml b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/gateway_userdata.yaml new file mode 100755 index 00000000..05538232 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/gateway_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenKey}\"" installationType=\"gateway\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"gateway\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/locals.tf b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/locals.tf new file mode 100755 index 00000000..a0d9034d --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/locals.tf @@ -0,0 +1,39 @@ +locals { + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [lambda_scheduled_interval] must be a valid hostname label or an empty string" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + volume_encryption_condition = var.volume_encryption != "" ? true : false + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) + gateway_password_hash_base64 = base64encode(var.gateway_password_hash) + gateway_maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/main.tf b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/main.tf new file mode 100755 index 00000000..38382cc2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/main.tf @@ -0,0 +1,63 @@ +resource "aws_launch_template" "gateway_launch_template" { + key_name = var.key_name + image_id = var.ami_id + instance_type = var.gateway_instance_type + description = "Initial launch template version" + + iam_instance_profile { + name = var.iam_instance_profile_id + } + + network_interfaces { + network_interface_id = var.external_eni_id + device_index = 0 + } + + network_interfaces { + network_interface_id = var.internal_eni_id + device_index = 1 + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } +} + +resource "aws_instance" "gateway_instance" { + launch_template { + id = aws_launch_template.gateway_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.gateway_name + x-chkp-tags = format("management=%s:template=%s:ip-address=%s", var.management_server, var.configuration_template, var.control_gateway_over_public_or_private_address) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition ? true : false + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + user_data = templatefile("${path.module}/gateway_userdata.yaml", { + // script's arguments + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.gateway_maintenance_mode_password_hash_base64, + Shell = var.admin_shell, + SICKey = local.gateway_SICkey_base64, + TokenKey = var.gateway_TokenKey, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + Hostname = var.gateway_hostname, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + EnableInstanceConnect = var.enable_instance_connect, + OsVersion = local.version_split + }) +} diff --git a/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/output.tf b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/output.tf new file mode 100755 index 00000000..0c5f6d02 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/output.tf @@ -0,0 +1,9 @@ +output "gateway_instance_id" { + value = aws_instance.gateway_instance.id +} +output "gateway_instance_arn" { + value = aws_instance.gateway_instance.arn +} +output "gateway_instance_name" { + value = aws_instance.gateway_instance.tags["Name"] +} diff --git a/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/variables.tf b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/variables.tf new file mode 100755 index 00000000..0e1a010c --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/gateway_instance/variables.tf @@ -0,0 +1,147 @@ +variable "external_eni_id" { + type = string + description = "The external-eni of the security gateway" +} +variable "internal_eni_id" { + type = string + description = "The internal-eni of the security gateway" +} +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway-tf" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the Security Gateway is provisioned using its private or public address" + default = "private" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')." + default = "alias/aws/ebs" +} +variable "gateway_version" { + type = string + description = "Gateway version & license" + default = "R81.20-BYOL" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance." + default = {} +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "ami_id" { + type = string + description = "The AMI to use for the instance" +} +variable "iam_instance_profile_id" { + type = string + description = "The IAM instance profile id" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional)" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "primary_ntp" { + type = string + description = "(Optional)" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional)" + default = "" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/instance_type/main.tf b/deprecated/terraform/aws/R80.40/modules/common/instance_type/main.tf new file mode 100755 index 00000000..22fffe49 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/instance_type/main.tf @@ -0,0 +1,353 @@ +locals { + gw_types = [ + "c4.large", + "c4.xlarge", + "c5.large", + "c5.xlarge", + "c5.2xlarge", + "c5.4xlarge", + "c5.9xlarge", + "c5.12xlarge", + "c5.18xlarge", + "c5.24xlarge", + "c5n.large", + "c5n.xlarge", + "c5n.2xlarge", + "c5n.4xlarge", + "c5n.9xlarge", + "c5n.18xlarge", + "c5d.large", + "c5d.xlarge", + "c5d.2xlarge", + "c5d.4xlarge", + "c5d.9xlarge", + "c5d.12xlarge", + "c5d.18xlarge", + "c5d.24xlarge", + "m5.large", + "m5.xlarge", + "m5.2xlarge", + "m5.4xlarge", + "m5.8xlarge", + "m5.12xlarge", + "m5.16xlarge", + "m5.24xlarge", + "m6i.large", + "m6i.xlarge", + "m6i.2xlarge", + "m6i.4xlarge", + "m6i.8xlarge", + "m6i.12xlarge", + "m6i.16xlarge", + "m6i.24xlarge", + "m6i.32xlarge", + "c6i.large", + "c6i.xlarge", + "c6i.2xlarge", + "c6i.4xlarge", + "c6i.8xlarge", + "c6i.12xlarge", + "c6i.16xlarge", + "c6i.24xlarge", + "c6i.32xlarge", + "c6in.large", + "c6in.xlarge", + "c6in.2xlarge", + "c6in.4xlarge", + "c6in.8xlarge", + "c6in.12xlarge", + "c6in.16xlarge", + "c6in.24xlarge", + "c6in.32xlarge", + "r5.large", + "r5.xlarge", + "r5.2xlarge", + "r5.4xlarge", + "r5.8xlarge", + "r5.12xlarge", + "r5.16xlarge", + "r5.24xlarge", + "r5a.large", + "r5a.xlarge", + "r5a.2xlarge", + "r5a.4xlarge", + "r5a.8xlarge", + "r5a.12xlarge", + "r5a.16xlarge", + "r5a.24xlarge", + "r5b.large", + "r5b.xlarge", + "r5b.2xlarge", + "r5b.4xlarge", + "r5b.8xlarge", + "r5b.12xlarge", + "r5b.16xlarge", + "r5b.24xlarge", + "r5n.large", + "r5n.xlarge", + "r5n.2xlarge", + "r5n.4xlarge", + "r5n.8xlarge", + "r5n.12xlarge", + "r5n.16xlarge", + "r5n.24xlarge", + "r6i.large", + "r6i.xlarge", + "r6i.2xlarge", + "r6i.4xlarge", + "r6i.8xlarge", + "r6i.12xlarge", + "r6i.16xlarge", + "r6i.24xlarge", + "r6i.32xlarge", + "m6a.large", + "m6a.xlarge", + "m6a.2xlarge", + "m6a.4xlarge", + "m6a.8xlarge", + "m6a.12xlarge", + "m6a.16xlarge", + "m6a.24xlarge", + "m6a.32xlarge", + "m6a.48xlarge" + ] + mgmt_types = [ + "c5.large", + "c5.xlarge", + "c5.2xlarge", + "c5.4xlarge", + "c5.9xlarge", + "c5.12xlarge", + "c5.18xlarge", + "c5.24xlarge", + "c5n.large", + "c5n.xlarge", + "c5n.2xlarge", + "c5n.4xlarge", + "c5n.9xlarge", + "c5n.18xlarge", + "c5d.large", + "c5d.xlarge", + "c5d.2xlarge", + "c5d.4xlarge", + "c5d.9xlarge", + "c5d.12xlarge", + "c5d.18xlarge", + "c5d.24xlarge", + "m5.large", + "m5.xlarge", + "m5.2xlarge", + "m5.4xlarge", + "m5.8xlarge", + "m5.12xlarge", + "m5.16xlarge", + "m5.24xlarge", + "m6i.large", + "m6i.xlarge", + "m6i.2xlarge", + "m6i.4xlarge", + "m6i.8xlarge", + "m6i.12xlarge", + "m6i.16xlarge", + "m6i.24xlarge", + "m6i.32xlarge", + "c6i.large", + "c6i.xlarge", + "c6i.2xlarge", + "c6i.4xlarge", + "c6i.8xlarge", + "c6i.12xlarge", + "c6i.16xlarge", + "c6i.24xlarge", + "c6i.32xlarge", + "c6in.large", + "c6in.xlarge", + "c6in.2xlarge", + "c6in.4xlarge", + "c6in.8xlarge", + "c6in.12xlarge", + "c6in.16xlarge", + "c6in.24xlarge", + "c6in.32xlarge", + "r5.large", + "r5.xlarge", + "r5.2xlarge", + "r5.4xlarge", + "r5.8xlarge", + "r5.12xlarge", + "r5.16xlarge", + "r5.24xlarge", + "r5a.large", + "r5a.xlarge", + "r5a.2xlarge", + "r5a.4xlarge", + "r5a.8xlarge", + "r5a.12xlarge", + "r5a.16xlarge", + "r5a.24xlarge", + "r5b.large", + "r5b.xlarge", + "r5b.2xlarge", + "r5b.4xlarge", + "r5b.8xlarge", + "r5b.12xlarge", + "r5b.16xlarge", + "r5b.24xlarge", + "r5n.large", + "r5n.xlarge", + "r5n.2xlarge", + "r5n.4xlarge", + "r5n.8xlarge", + "r5n.12xlarge", + "r5n.16xlarge", + "r5n.24xlarge", + "r6i.large", + "r6i.xlarge", + "r6i.2xlarge", + "r6i.4xlarge", + "r6i.8xlarge", + "r6i.12xlarge", + "r6i.16xlarge", + "r6i.24xlarge", + "r6i.32xlarge", + "m6a.large", + "m6a.xlarge", + "m6a.2xlarge", + "m6a.4xlarge", + "m6a.8xlarge", + "m6a.12xlarge", + "m6a.16xlarge", + "m6a.24xlarge", + "m6a.32xlarge", + "m6a.48xlarge" + ] + mds_types = [ + "c5.large", + "c5.xlarge", + "c5.2xlarge", + "c5.4xlarge", + "c5.9xlarge", + "c5.12xlarge", + "c5.18xlarge", + "c5.24xlarge", + "c5n.large", + "c5n.xlarge", + "c5n.2xlarge", + "c5n.4xlarge", + "c5n.9xlarge", + "c5n.18xlarge", + "c5d.large", + "c5d.xlarge", + "c5d.2xlarge", + "c5d.4xlarge", + "c5d.9xlarge", + "c5d.12xlarge", + "c5d.18xlarge", + "c5d.24xlarge", + "m5.large", + "m5.xlarge", + "m5.2xlarge", + "m5.4xlarge", + "m5.8xlarge", + "m5.12xlarge", + "m5.16xlarge", + "m5.24xlarge", + "m6i.large", + "m6i.xlarge", + "m6i.2xlarge", + "m6i.4xlarge", + "m6i.8xlarge", + "m6i.12xlarge", + "m6i.16xlarge", + "m6i.24xlarge", + "m6i.32xlarge", + "c6i.large", + "c6i.xlarge", + "c6i.2xlarge", + "c6i.4xlarge", + "c6i.8xlarge", + "c6i.12xlarge", + "c6i.16xlarge", + "c6i.24xlarge", + "c6i.32xlarge", + "c6in.large", + "c6in.xlarge", + "c6in.2xlarge", + "c6in.4xlarge", + "c6in.8xlarge", + "c6in.12xlarge", + "c6in.16xlarge", + "c6in.24xlarge", + "c6in.32xlarge", + "r5.large", + "r5.xlarge", + "r5.2xlarge", + "r5.4xlarge", + "r5.8xlarge", + "r5.12xlarge", + "r5.16xlarge", + "r5.24xlarge", + "r5a.large", + "r5a.xlarge", + "r5a.2xlarge", + "r5a.4xlarge", + "r5a.8xlarge", + "r5a.12xlarge", + "r5a.16xlarge", + "r5a.24xlarge", + "r5b.large", + "r5b.xlarge", + "r5b.2xlarge", + "r5b.4xlarge", + "r5b.8xlarge", + "r5b.12xlarge", + "r5b.16xlarge", + "r5b.24xlarge", + "r5n.large", + "r5n.xlarge", + "r5n.2xlarge", + "r5n.4xlarge", + "r5n.8xlarge", + "r5n.12xlarge", + "r5n.16xlarge", + "r5n.24xlarge", + "r6i.large", + "r6i.xlarge", + "r6i.2xlarge", + "r6i.4xlarge", + "r6i.8xlarge", + "r6i.12xlarge", + "r6i.16xlarge", + "r6i.24xlarge", + "r6i.32xlarge", + "m6a.large", + "m6a.xlarge", + "m6a.2xlarge", + "m6a.4xlarge", + "m6a.8xlarge", + "m6a.12xlarge", + "m6a.16xlarge", + "m6a.24xlarge", + "m6a.32xlarge", + "m6a.48xlarge" + ] + server_types = [ + "t3.nano", + "t3.micro", + "t3.small", + "t3.medium", + "t3.large", + "t3.xlarge", + "t3.2xlarge" + ] +} + +locals { + gw_values = var.chkp_type == "gateway" ? local.gw_types : [] + mgmt_values = var.chkp_type == "management" ? local.mgmt_types : [] + mds_values = var.chkp_type == "mds" ? local.mds_types : [] + server_values = var.chkp_type == "server" ? local.server_types : [] + sa_values = var.chkp_type == "standalone" ? concat(local.gw_types, local.mgmt_types) : [] + allowed_values = coalescelist(local.gw_values, local.mgmt_values, local.mds_values, local.sa_values , local.server_types) + is_allowed_type = index(local.allowed_values, var.instance_type) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/instance_type/variables.tf b/deprecated/terraform/aws/R80.40/modules/common/instance_type/variables.tf new file mode 100755 index 00000000..1711c3f7 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/instance_type/variables.tf @@ -0,0 +1,22 @@ +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +locals { + type_allowed_values = [ + "gateway", + "management", + "mds", + "standalone", + "server" + ] + // Will fail if var.chkp_type is invalid + validate_instance_type = index(local.type_allowed_values, var.chkp_type) +} + +variable "instance_type" { + type = string + description = "AWS Instance type" +} + diff --git a/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/locals.tf b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/locals.tf new file mode 100755 index 00000000..493c4d9a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/locals.tf @@ -0,0 +1,3 @@ +locals { + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/main.tf b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/main.tf new file mode 100755 index 00000000..ddcb5bd8 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/main.tf @@ -0,0 +1,6 @@ +resource "aws_route" "internal_default_route" { + count = local.internal_route_table_condition + route_table_id = var.private_route_table + destination_cidr_block = "0.0.0.0/0" + network_interface_id = var.internal_eni_id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/output.tf b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/output.tf new file mode 100755 index 00000000..fa691b92 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/output.tf @@ -0,0 +1,3 @@ +output "internal_default_route_id" { + value = aws_route.internal_default_route.*.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/variables.tf b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/variables.tf new file mode 100755 index 00000000..b8e2f458 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/internal_default_route/variables.tf @@ -0,0 +1,9 @@ +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Gateway instance in the specified route table (e.g. rtb-12a34567)" + default="" +} +variable "internal_eni_id" { + type = string + description = "The internal-eni of the security gateway" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/load_balancer/main.tf b/deprecated/terraform/aws/R80.40/modules/common/load_balancer/main.tf new file mode 100755 index 00000000..18b3b753 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/load_balancer/main.tf @@ -0,0 +1,36 @@ +resource "random_id" "unique_lb_id" { + keepers = { + prefix = var.prefix_name + } + byte_length = 8 +} +resource "aws_lb" "load_balancer" { + name = substr(format("%s-%s", "${var.prefix_name}-LB", random_id.unique_lb_id.hex), 0, 32) + load_balancer_type = var.load_balancers_type == "gateway" ? "gateway" : var.load_balancers_type == "Network Load Balancer" ? "network": "application" + internal = var.load_balancers_type == "gateway" ? "false" : var.internal + subnets = var.instances_subnets + security_groups = var.security_groups + tags = var.tags + enable_cross_zone_load_balancing = var.cross_zone_load_balancing +} +resource "aws_lb_target_group" "lb_target_group" { + name = substr(format("%s-%s", "${var.prefix_name}-TG", random_id.unique_lb_id.hex), 0, 32) + vpc_id = var.vpc_id + protocol = var.load_balancer_protocol + port = var.target_group_port + health_check { + port = var.load_balancers_type != "gateway" ? var.health_check_port : 8117 + protocol = var.load_balancers_type != "gateway" ? var.health_check_protocol : "TCP" + } +} +resource "aws_lb_listener" "lb_listener" { + depends_on = [aws_lb.load_balancer, aws_lb_target_group.lb_target_group] + load_balancer_arn = aws_lb.load_balancer.arn + certificate_arn = var.certificate_arn + protocol = var.load_balancers_type != "gateway" ? var.load_balancer_protocol : null + port = var.load_balancers_type != "gateway" ? var.listener_port : null + default_action { + type = "forward" + target_group_arn = aws_lb_target_group.lb_target_group.arn + } +} diff --git a/deprecated/terraform/aws/R80.40/modules/common/load_balancer/output.tf b/deprecated/terraform/aws/R80.40/modules/common/load_balancer/output.tf new file mode 100755 index 00000000..63123606 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/load_balancer/output.tf @@ -0,0 +1,18 @@ +output "load_balancer_id" { + value = aws_lb.load_balancer.id +} +output "load_balancer_arn" { + value = aws_lb.load_balancer.arn +} +output "load_balancer_url" { + value = aws_lb.load_balancer.dns_name +} +output "target_group_id" { + value = aws_lb_target_group.lb_target_group.id +} +output "target_group_arn" { + value = aws_lb_target_group.lb_target_group.arn +} +output "load_balancer_tags" { + value = aws_lb.load_balancer.tags +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/load_balancer/variables.tf b/deprecated/terraform/aws/R80.40/modules/common/load_balancer/variables.tf new file mode 100755 index 00000000..2e143fc7 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/load_balancer/variables.tf @@ -0,0 +1,62 @@ +variable "instances_subnets" { + type = list(string) + description = "Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} +variable "prefix_name" { + type = string + description = "Load Balancer and Target Group prefix name" + default = "quickstart" +} +variable "internal" { + type = bool + description = "Select 'true' to create an Internal Load Balancer." + default = false +} +variable "security_groups" { + type = list(string) + description = "A list of security group IDs to assign to the LB. Only valid for Load Balancers of type application" +} +variable "tags" { + type = map(string) + description = "A map of tags to assign to the load balancer." +} +variable "vpc_id" { + type = string +} +variable "load_balancers_type" { + type = string + description = "Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing" + default = "Network Load Balancer" +} +variable "load_balancer_protocol" { + type = string + description = "The protocol to use on the Load Balancer." +} +variable "target_group_port" { + type = number + description = "The port on which targets receive traffic." +} +variable "listener_port" { + type = string + description = "The port on which the load balancer is listening." +} +variable "certificate_arn" { + type = string + description = "The ARN of the default server certificate. Exactly one certificate is required if the protocol is HTTPS or TLS. " + default = "" +} +variable "cross_zone_load_balancing"{ + type = bool + default = false + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." +} +variable "health_check_port" { + description = "The health check port" + type = number + default = null +} +variable "health_check_protocol" { + description = "The health check protocol" + type = string + default = null +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/main.tf b/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/main.tf new file mode 100755 index 00000000..265f3c56 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/main.tf @@ -0,0 +1,20 @@ +resource "aws_security_group" "permissive_sg" { + description = "Permissive security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + name_prefix = format("%s-PermissiveSecurityGroup", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) // Group name + tags = { + Name = format("%s-PermissiveSecurityGroup", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) // Resource name + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/output.tf b/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/output.tf new file mode 100755 index 00000000..83541c15 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/output.tf @@ -0,0 +1,9 @@ +output "permissive_sg_id" { + value = aws_security_group.permissive_sg.id +} +output "permissive_sg_name" { + value = aws_security_group.permissive_sg.name +} +output "permissive_sg_arn" { + value = aws_security_group.permissive_sg.arn +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/variables.tf b/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/variables.tf new file mode 100755 index 00000000..d2afaad2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/permissive_sg/variables.tf @@ -0,0 +1,13 @@ +variable "vpc_id" { + type = string +} +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway-tf" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/common/version_license/main.tf b/deprecated/terraform/aws/R80.40/modules/common/version_license/main.tf new file mode 100755 index 00000000..4b53b80a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/version_license/main.tf @@ -0,0 +1,71 @@ +locals { + gw_versions = [ + "R80.40-BYOL", + "R80.40-PAYG-NGTP", + "R80.40-PAYG-NGTX", + "R81-BYOL", + "R81-PAYG-NGTP", + "R81-PAYG-NGTX", + "R81.10-BYOL", + "R81.10-PAYG-NGTP", + "R81.10-PAYG-NGTX", + "R81.20-BYOL", + "R81.20-PAYG-NGTP", + "R81.20-PAYG-NGTX", + "R82-BYOL", + "R82-PAYG-NGTP", + "R82-PAYG-NGTX" + ] + mgmt_versions = [ + "R80.40-BYOL", + "R80.40-PAYG", + "R81-BYOL", + "R81-PAYG", + "R81.10-BYOL", + "R81.10-PAYG", + "R81.20-BYOL", + "R81.20-PAYG", + "R82-BYOL", + "R82-PAYG" + ] + mds_versions = [ + "R80.40-BYOL", + "R81-BYOL", + "R81.10-BYOL", + "R81.20-BYOL", + "R82-BYOL" + ] + standalone_versions = [ + "R80.40-BYOL", + "R80.40-PAYG-NGTP", + "R81-BYOL", + "R81-PAYG-NGTP", + "R81.10-BYOL", + "R81.10-PAYG-NGTP", + "R81.20-BYOL", + "R81.20-PAYG-NGTP", + "R82-BYOL", + "R82-PAYG-NGTP" + ] + gwlb_gw_versions = [ + "R80.40-BYOL", + "R80.40-PAYG-NGTP", + "R80.40-PAYG-NGTX", + "R81.20-BYOL", + "R81.20-PAYG-NGTP", + "R81.20-PAYG-NGTX", + "R82-BYOL", + "R82-PAYG-NGTP", + "R82-PAYG-NGTX" + ] +} + +locals { + gw_values = var.chkp_type == "gateway" ? local.gw_versions : [] + mgmt_values = var.chkp_type == "management" ? local.mgmt_versions : [] + mds_values = var.chkp_type == "mds" ? local.mds_versions : [] + standalone_values = var.chkp_type == "standalone" ? local.standalone_versions : [] + gwlb_gw_values = var.chkp_type == "gwlb_gw" ? local.gwlb_gw_versions : [] + allowed_values = coalescelist(local.gw_values, local.mgmt_values, local.standalone_values, local.mds_values, local.gwlb_gw_values) + is_allowed_type = index(local.allowed_values, var.version_license) +} diff --git a/deprecated/terraform/aws/R80.40/modules/common/version_license/variables.tf b/deprecated/terraform/aws/R80.40/modules/common/version_license/variables.tf new file mode 100755 index 00000000..9467e232 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/common/version_license/variables.tf @@ -0,0 +1,21 @@ +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +locals { + type_allowed_values = [ + "gateway", + "management", + "mds", + "standalone", + "gwlb_gw"] + // Will fail if var.chkp_type is invalid + validate_chkp_type = index(local.type_allowed_values, var.chkp_type) +} + +variable "version_license" { + type = string + description = "AWS Version license" +} + diff --git a/deprecated/terraform/aws/R80.40/modules/custom-autoscale/locals.tf b/deprecated/terraform/aws/R80.40/modules/custom-autoscale/locals.tf new file mode 100755 index 00000000..1a9b6900 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/custom-autoscale/locals.tf @@ -0,0 +1,9 @@ +locals { + asg_name = format("%s%s-servers", var.prefix != "" ? format("%s-", var.prefix) : "", var.asg_name) + + regex_valid_server_ami = "^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$" + // Will fail if var.server_ami is invalid + regex_server_ami = regex(local.regex_valid_server_ami, var.server_ami) == var.server_ami ? 0 : "Amazon Machine Image ID must be in the form ami-xxxxxxxx or ami-xxxxxxxxxxxxxxxxx" + + provided_target_groups_condition = var.servers_target_groups != "" ? true : false +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/custom-autoscale/main.tf b/deprecated/terraform/aws/R80.40/modules/custom-autoscale/main.tf new file mode 100755 index 00000000..c361388d --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/custom-autoscale/main.tf @@ -0,0 +1,94 @@ +resource "aws_security_group" "servers_security_group" { + count = var.deploy_internal_security_group ? 1 : 0 + name_prefix = format("%s_ServersSecurityGroup", local.asg_name) + description = "Servers security group" + vpc_id = var.vpc_id + + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + + tags = { + Name = format("%s_ServersSecurityGroup", local.asg_name) + } +} + + +resource "aws_launch_template" "servers_launch_template" { + name_prefix = local.asg_name + network_interfaces { + associate_public_ip_address = var.allocate_public_address + security_groups = var.deploy_internal_security_group ? [aws_security_group.servers_security_group[0].id] : [var.source_security_group] + } + key_name = var.key_name + image_id = var.server_ami + description = "Initial template version" + monitoring { + enabled = true + } + instance_type = var.servers_instance_type +} +resource "aws_autoscaling_group" "servers_group" { + name_prefix = local.asg_name + vpc_zone_identifier = var.servers_subnets + launch_template { + name = aws_launch_template.servers_launch_template.name + version = aws_launch_template.servers_launch_template.latest_version + } + min_size = var.servers_min_group_size + max_size = var.servers_max_group_size + target_group_arns = local.provided_target_groups_condition ? [var.servers_target_groups] : [] + + tag { + key = "Name" + value = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.server_name) + propagate_at_launch = true + } +} +resource "aws_autoscaling_policy" "scale_up_policy" { + adjustment_type = "ChangeInCapacity" + autoscaling_group_name = aws_autoscaling_group.servers_group.name + name = "scale_up_policy" + cooldown = 300 + scaling_adjustment = 1 +} +resource "aws_autoscaling_policy" "scale_down_policy" { + adjustment_type = "ChangeInCapacity" + autoscaling_group_name = aws_autoscaling_group.servers_group.name + name = "scale_down_policy" + cooldown = 300 + scaling_adjustment = -1 +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_high" { + alarm_description = "Scale-up if CPU > 80% for 10 minutes" + metric_name = "CPUUtilization" + namespace = "AWS/EC2" + statistic = "Average" + period = "300" + evaluation_periods = "2" + threshold = "80" + alarm_actions = [aws_autoscaling_policy.scale_up_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.servers_group.name + } + comparison_operator = "GreaterThanThreshold" + alarm_name = "cpu_alarm_high" +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_low" { + alarm_description = "Scale-down if CPU < 60% for 10 minutes" + metric_name = "CPUUtilization" + namespace = "AWS/EC2" + statistic = "Average" + period = "300" + evaluation_periods = "2" + threshold = "60" + alarm_actions = [aws_autoscaling_policy.scale_down_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.servers_group.name + } + comparison_operator = "LessThanThreshold" + alarm_name = "cpu_alarm_low" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/custom-autoscale/variables.tf b/deprecated/terraform/aws/R80.40/modules/custom-autoscale/variables.tf new file mode 100755 index 00000000..a99cb9a5 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/custom-autoscale/variables.tf @@ -0,0 +1,89 @@ +// Module: Auto Scaling group of workload servers + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string + description = "Select an existing VPC" +} +variable "servers_subnets" { + type = list(string) + description = "Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-0d72417c,subnet-1f61306f,subnet-1061d06f)" +} + +// --- EC2 Instances Configuration --- +variable "server_ami" { + type = string + description = "The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63)" +} +variable "server_name" { + type = string + description = "AMI of the servers" + default = "Server-tf" +} +variable "servers_instance_type" { + type = string + description = "The EC2 instance type for the web servers" + default = "t3.micro" +} +module "validate_servers_instance_type" { + source = "../common/instance_type" + + chkp_type = "server" + instance_type = var.servers_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "allocate_public_address" { + type = bool + description = "Allocate an elastic IP for each server" + default = false +} + +// --- Auto Scaling Configuration --- +variable "servers_min_group_size" { + type = number + description = "The minimal number of servers in the Auto Scaling group" + default = 2 +} +resource "null_resource" "servers_min_group_size_too_small" { + // servers_min_group_size validation - resource will not be created if the size is smaller than 1 + count = var.servers_min_group_size >= 1 ? 0 : "servers_min_group_size must be at least 1" +} +variable "servers_max_group_size" { + type = number + description = "The maximal number of servers in the Auto Scaling group" + default = 10 +} +resource "null_resource" "servers_max_group_size_too_small" { + // servers_max_group_size validation - resource will not be created if the size is smaller than 1 + count = var.servers_max_group_size >= 1 ? 0 : "servers_max_group_size must be at least 1" +} +variable "servers_target_groups" { + type = string + description = "(Optional) An optional list of Target Groups to associate with the Auto Scaling group (comma separated list of ARNs, without spaces)" + default = "" +} +variable "deploy_internal_security_group" { + type = bool + description = "Select 'false' to use an existing Security group" + default = true +} +variable "source_security_group" { + type = string + description = "The ID of Security Group from which access will be allowed to the instances in this Auto Scaling group" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/modules/vpc/main.tf b/deprecated/terraform/aws/R80.40/modules/vpc/main.tf new file mode 100755 index 00000000..b4b223b8 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/vpc/main.tf @@ -0,0 +1,66 @@ +// --- VPC --- +resource "aws_vpc" "vpc" { + cidr_block = var.vpc_cidr +} + +// --- Internet Gateway --- +resource "aws_internet_gateway" "igw" { + vpc_id = aws_vpc.vpc.id +} + +// --- Public Subnets --- +resource "aws_subnet" "public_subnets" { + for_each = var.public_subnets_map + + vpc_id = aws_vpc.vpc.id + availability_zone = each.key + cidr_block = cidrsubnet(aws_vpc.vpc.cidr_block, var.subnets_bit_length, each.value) + map_public_ip_on_launch = true + tags = { + Name = format("Public subnet %s", each.value) + } +} + +// --- Private Subnets --- +resource "aws_subnet" "private_subnets" { + for_each = var.private_subnets_map + + vpc_id = aws_vpc.vpc.id + availability_zone = each.key + cidr_block = cidrsubnet(aws_vpc.vpc.cidr_block, var.subnets_bit_length, each.value) + tags = { + Name = format("Private subnet %s", each.value) + } +} + +// --- tgw Subnets --- +resource "aws_subnet" "tgw_subnets" { + for_each = var.tgw_subnets_map + + vpc_id = aws_vpc.vpc.id + availability_zone = each.key + cidr_block = cidrsubnet(aws_vpc.vpc.cidr_block, var.subnets_bit_length, each.value) + tags = { + Name = format("tgw subnet %s", each.value) + } +} + + +// --- Routes --- +resource "aws_route_table" "public_subnet_rtb" { + vpc_id = aws_vpc.vpc.id + tags = { + Name = "Public Subnets Route Table" + } +} +resource "aws_route" "vpc_internet_access" { + route_table_id = aws_route_table.public_subnet_rtb.id + destination_cidr_block = "0.0.0.0/0" + gateway_id = aws_internet_gateway.igw.id +} +resource "aws_route_table_association" "public_rtb_to_public_subnets" { + for_each = { for public_subnet in aws_subnet.public_subnets : public_subnet.cidr_block => public_subnet.id } + route_table_id = aws_route_table.public_subnet_rtb.id + subnet_id = each.value +} + diff --git a/deprecated/terraform/aws/R80.40/modules/vpc/output.tf b/deprecated/terraform/aws/R80.40/modules/vpc/output.tf new file mode 100755 index 00000000..fc4173c9 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/vpc/output.tf @@ -0,0 +1,18 @@ +output "vpc_id" { + value = aws_vpc.vpc.id +} +output "public_subnets_ids_list" { + value = [for public_subnet in aws_subnet.public_subnets : public_subnet.id ] +} +output "private_subnets_ids_list" { + value = [for private_subnet in aws_subnet.private_subnets : private_subnet.id] +} +output "tgw_subnets_ids_list" { + value = [for tgw_subnet in aws_subnet.tgw_subnets : tgw_subnet.id] +} +output "public_rtb" { + value = aws_route_table.public_subnet_rtb.id +} +output "aws_igw" { + value = aws_internet_gateway.igw.id +} diff --git a/deprecated/terraform/aws/R80.40/modules/vpc/variables.tf b/deprecated/terraform/aws/R80.40/modules/vpc/variables.tf new file mode 100755 index 00000000..2623f9d0 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/modules/vpc/variables.tf @@ -0,0 +1,22 @@ +variable "vpc_cidr" { + type = string +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "tgw_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + default = {} +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20." +} + diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale-master/README.md b/deprecated/terraform/aws/R80.40/qs-autoscale-master/README.md new file mode 100755 index 00000000..54c7049b --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale-master/README.md @@ -0,0 +1,256 @@ +# Check Point CloudGuard Network Quick Start Auto Scaling Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group in a new VPC. + +These types of Terraform resources are supported: +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Subnet](https://www.terraform.io/docs/providers/aws/r/subnet.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Load Balancer](https://www.terraform.io/docs/providers/aws/r/lb.html) +* [Load Balancer Target Group](https://www.terraform.io/docs/providers/aws/r/lb_target_group.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Check Point CloudGuard Auto Scaling on AWS](https://aws.amazon.com/quickstart/architecture/check-point-cloudguard/) for additional information + +This solution uses the following modules: +- /terraform/aws/qs-autoscale +- /terraform/aws/autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/qs-autoscale, /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/qs-autoscale, /terraform/aws/autoscale and /terraform/aws/management: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/qs-autoscale-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/qs-autoscale-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "TF" + asg_name = "asg-qs" + + // --- Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 + } + subnets_bit_length = 8 + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + provision_tag = "quickstart" + load_balancers_type = "Network Load Balancer" + LB_protocol = "TCP" + certificate = "arn:aws:iam::12345678:server-certificate/certificate" + service_port = "80" + admin_shell = "/etc/cli.sh" + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = false + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + + // --- Web Servers Auto Scaling Group Configuration --- + servers_deploy = true + servers_instance_type = "t3.micro" + server_ami = "ami-12345abc" + ``` + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` + - To deploy web servers: + ``` + servers_deploy = true + ``` + - To create an ASG configuration without a proxy ELB: + ``` + proxy_elb_type= "none" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| provision_tag | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | quickstart | no | +| load_balancers_type | Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing | string | - Network Load Balancer
- Application Load Balancer
| Network Load Balancer | no | +| load_balancer_protocol | The protocol to use on the Load Balancer | string | Network Load Balancer:
- TCP
- TLS
- UDP
- TCP_UDP

Application Load Balancer:
- HTTP
- HTTPS | TCP | yes | +| certificate | Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP | string | n/a | n/a | no | +| service_port | The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS | string | n/a | n/a | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | list(string) | n/a | n/a | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| servers_deploy | Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored | bool | true/false | false | no | +| servers_subnets | Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-0d72417c,subnet-1f61306f,subnet-1061d06f). | list(string) | n/a | n/a | yes | +| servers_instance_type | The EC2 instance type for the web servers | string | - t3.nano
- t3.micro
- t3.small
- t3.medium
- t3.large
- t3.xlarge
- t3.2xlarge | t3.micro | no | +| server_ami | The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63) | string | n/a | n/a | yes | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + + +## Outputs +| Name | Description | +|----------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| public_subnets_ids_list | A list of the public subnets ids | +| private_subnets_ids_list | A list of the private subnets ids | +| public_rout_table | The public route table id | +| internal_port | The internal Load Balancer should listen to this port | +| management_name | The deployed Security Management AWS instance name | +| load_balancer_url | The URL of the external Load Balancer | +| external_load_balancer_arn | The external Load Balancer ARN | +| internal_load_balancer_arn | The internal Load Balancer ARN | +| external_lb_target_group_arn | The external Load Balancer Target Group ARN | +| internal_lb_target_group_arn | The internal Load Balancer Target Group ARN | +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------| +| 20240425 | Remove support for R81 and lower versions | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231127 | Add support for parameter admin shell | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Quick Start Auto Scaling Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale-master/locals.tf b/deprecated/terraform/aws/R80.40/qs-autoscale-master/locals.tf new file mode 100755 index 00000000..e23f58a2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale-master/locals.tf @@ -0,0 +1,63 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + regex_valid_provision_tag = "^[a-zA-Z0-9-]{1,12}$" + // Will fail if var.provision_tag is invalid + regex_provision_tag = regex(local.regex_valid_provision_tag, var.provision_tag) == var.provision_tag ? 0 : "Variable [provision_tag] must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + + load_balancers_type_allowed_values = [ + "Network Load Balancer", + "Application Load Balancer"] + // Will fail if var.load_balancers_type is invalid + validate_load_balancers_type = index(local.load_balancers_type_allowed_values, var.load_balancers_type) + + lb_protocol_allowed_values = var.load_balancers_type == "Network Load Balancer" ? [ + "TCP", + "TLS", + "UDP", + "TCP_UDP"] : [ + "HTTP", + "HTTPS"] + // Will fail if var.load_balancer_protocol is invalid + validate_lb_protocol = index(local.lb_protocol_allowed_values, var.load_balancer_protocol) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_certificate = "^(arn:aws:[a-z]+::[0-9]{12}:server-certificate/[a-zA-Z0-9-]*)?$" + // Will fail if var.certificate is invalid + regex_certificate = regex(local.regex_valid_certificate, var.certificate) == var.certificate ? 0 : "Variable [certificate] must be a valid Amazon Resource Name (ARN), for example: arn:aws:iam::123456789012:server-certificate/web-server-certificate" + + regex_valid_service_port = "^([0-9]{1,4}|[1-5][0-9]{4}|6[0-4][0-9]{3}|65[0-4][0-9]{2}|655[0-2][0-9]|6553[0-5])?$" + // Will fail if var.service_port is invalid + regex_service_port = regex(local.regex_valid_service_port, var.service_port) == var.service_port ? 0 : "Custom service port must be a number between 0 and 65535" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash." + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters." + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash." + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR." + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses." + + + regex_valid_server_ami = "^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$" + // Will fail if var.server_ami is invalid + regex_server_ami = regex(local.regex_valid_server_ami, var.server_ami) == var.server_ami ? 0 : "Amazon Machine Image ID must be in the form ami-xxxxxxxx or ami-xxxxxxxxxxxxxxxxx" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale-master/main.tf b/deprecated/terraform/aws/R80.40/qs-autoscale-master/main.tf new file mode 100755 index 00000000..9c7eada0 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale-master/main.tf @@ -0,0 +1,60 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +module "launch_qs_autoscale" { + source = "../qs-autoscale" + providers = { + aws = aws + } + + region = var.region + prefix = var.prefix + asg_name = var.asg_name + vpc_id = module.launch_vpc.vpc_id + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + provision_tag = var.provision_tag + load_balancers_type = var.load_balancers_type + load_balancer_protocol = var.load_balancer_protocol + certificate = var.certificate + service_port = var.service_port + admin_shell = var.admin_shell + gateways_subnets = module.launch_vpc.public_subnets_ids_list + gateway_instance_type = var.gateway_instance_type + gateways_min_group_size = var.gateways_min_group_size + gateways_max_group_size = var.gateways_max_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + enable_cloudwatch = var.enable_cloudwatch + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.gateway_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateways_blades = var.gateways_blades + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + servers_deploy= var.servers_deploy + servers_subnets = module.launch_vpc.private_subnets_ids_list + servers_instance_type = var.servers_instance_type + server_ami = var.server_ami +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale-master/output.tf b/deprecated/terraform/aws/R80.40/qs-autoscale-master/output.tf new file mode 100755 index 00000000..1130dfe0 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale-master/output.tf @@ -0,0 +1,58 @@ +output "Deployment" { + value = module.launch_qs_autoscale.Deployment +} + +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "private_subnets_ids_list" { + value = module.launch_vpc.private_subnets_ids_list +} +output "public_rout_table" { + value = module.launch_vpc.public_rtb +} + +output "management_name" { + value = module.launch_qs_autoscale.management_name +} +output "internal_port" { + value = module.launch_qs_autoscale.internal_port +} +output "load_balancer_url" { + value = module.launch_qs_autoscale.load_balancer_url +} +output "external_load_balancer_arn" { + value = module.launch_qs_autoscale.external_load_balancer_arn +} +output "internal_load_balancer_arn" { + value = module.launch_qs_autoscale.internal_load_balancer_arn +} +output "external_lb_target_group_arn" { + value = module.launch_qs_autoscale.external_lb_target_group_arn +} +output "internal_lb_target_group_arn" { + value = module.launch_qs_autoscale.internal_lb_target_group_arn +} + +output "autoscale_autoscaling_group_name" { + value = module.launch_qs_autoscale.autoscale_autoscaling_group_name +} +output "autoscale_autoscaling_group_arn" { + value = module.launch_qs_autoscale.autoscale_autoscaling_group_arn +} +output "autoscale_security_group_id" { + value = module.launch_qs_autoscale.autoscale_security_group_id +} +output "autoscale_iam_role_name" { + value = module.launch_qs_autoscale.autoscale_iam_role_name +} + +output "configuration_template" { + value = module.launch_qs_autoscale.configuration_template +} +output "controller_name" { + value = module.launch_qs_autoscale.controller_name +} diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/qs-autoscale-master/terraform.tfvars new file mode 100755 index 00000000..37a07774 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale-master/terraform.tfvars @@ -0,0 +1,57 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "TF" +asg_name = "asg-qs" + +// --- Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 +} +subnets_bit_length = 8 + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +provision_tag = "quickstart" +load_balancers_type = "Application Load Balancer" +load_balancer_protocol = "HTTP" +certificate = "" +service_port = "80" +admin_shell = "/etc/cli.sh" + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Web Servers Auto Scaling Group Configuration --- +servers_deploy = true +servers_instance_type = "t3.micro" +server_ami = "ami-12345abc" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale-master/variables.tf b/deprecated/terraform/aws/R80.40/qs-autoscale-master/variables.tf new file mode 100755 index 00000000..317b1c94 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale-master/variables.tf @@ -0,0 +1,240 @@ +// Module: Check Point CloudGuard Network Quick Start Auto Scaling +//Deploy a Check Point CloudGuard Network Security Gateways Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group in a new VPC. + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} +// --- Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "provision_tag" { + type = string + description = "The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + default = "quickstart" +} +variable "load_balancers_type" { + type = string + description = "Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing" + default = "Network Load Balancer" +} +variable "load_balancer_protocol" { + type = string + description = "The protocol to use on the Load Balancer" +} +variable "certificate" { + type = string + description = "Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP" +} +variable "service_port" { + type = string + description = "The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS" +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Web Servers Auto Scaling Group Configuration --- +variable "servers_deploy" { + type = bool + description = "Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored" + default = false +} +variable "servers_instance_type" { + type = string + description = "The EC2 instance type for the web servers" + default = "t3.micro" +} +module "validate_servers_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "server" + instance_type = var.servers_instance_type +} +variable "server_ami" { + type = string + description = "The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63)" +} diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale-master/versions.tf b/deprecated/terraform/aws/R80.40/qs-autoscale-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale/README.md b/deprecated/terraform/aws/R80.40/qs-autoscale/README.md new file mode 100755 index 00000000..823b454e --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale/README.md @@ -0,0 +1,238 @@ +# Check Point CloudGuard Network Quick Start Auto Scaling Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Load Balancer](https://www.terraform.io/docs/providers/aws/r/lb.html) +* [Load Balancer Target Group](https://www.terraform.io/docs/providers/aws/r/lb_target_group.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Check Point CloudGuard Auto Scaling on AWS](https://aws.amazon.com/quickstart/architecture/check-point-cloudguard/) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale +- /terraform/aws/modules/custom-autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/qs-autoscale/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "TF" + asg_name = "asg-qs" + + // --- General Settings --- + vpc_id = "vpc-12345678" + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + provision_tag = "quickstart" + load_balancers_type = "Application Load Balancer" + load_balancer_protocol = "HTTP" + certificate = "" + service_port = "80" + admin_shell = "/etc/cli.sh" + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = true + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + + // --- Web Servers Auto Scaling Group Configuration --- + servers_deploy = false + servers_subnets = ["subnet-1234abcd", "subnet-56789def"] + servers_instance_type = "t3.micro" + server_ami = "ami-12345678" + ``` + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` + - To deploy web servers: + ``` + servers_deploy = true + ``` + - To create an ASG configuration without a proxy ELB: + ``` + proxy_elb_type= "none" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| provision_tag | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | quickstart | no | +| load_balancers_type | Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing | string | - Network Load Balancer
- Application Load Balancer
| Network Load Balancer | no | +| load_balancer_protocol | The protocol to use on the Load Balancer | string | Network Load Balancer:
- TCP
- TLS
- UDP
- TCP_UDP

Application Load Balancer:
- HTTP
- HTTPS | TCP | yes | +| certificate | Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP | string | n/a | n/a | no | +| service_port | The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS | string | n/a | n/a | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | list(string) | n/a | n/a | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| servers_deploy | Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored | bool | true/false | false | no | +| servers_subnets | Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-0d72417c,subnet-1f61306f,subnet-1061d06f). | list(string) | n/a | n/a | yes | +| servers_instance_type | The EC2 instance type for the web servers | string | - t3.nano
- t3.micro
- t3.small
- t3.medium
- t3.large
- t3.xlarge
- t3.2xlarge | t3.micro | no | +| server_ami | The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63) | string | n/a | n/a | yes | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|----------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| management_name | The deployed Security Management AWS instance name | +| internal_port | The internal Load Balancer should listen to this port | +| load_balancer_url | The URL of the external Load Balancer | +| external_load_balancer_arn | The external Load Balancer ARN | +| internal_load_balancer_arn | The internal Load Balancer ARN | +| external_LB_target_group_arn | The external Load Balancer Target Group ARN | +| internal_LB_target_group_arn | The internal Load Balancer Target Group ARN | +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------------------------| +| 20240425 | Remove support for R81 and lower versions | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240130 | Network Load Balancer Health Check configuration change for higher than R81 version. New Health Check Port is 8117 and Protocol TCP | +| 20231127 | Add support for parameter admin shell | +| 20231022 | Fixed template to populate x-chkp-tags correctly | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Quick Start Auto Scaling Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale/locals.tf b/deprecated/terraform/aws/R80.40/qs-autoscale/locals.tf new file mode 100755 index 00000000..2ecac5dd --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale/locals.tf @@ -0,0 +1,71 @@ +locals { + load_balancer_name = format("%sLB", var.prefix != "" ? format("%s-", var.prefix) : "") + target_group_name = format("%sTG", var.prefix != "" ? format("%s-", var.prefix) : "") + regex_valid_provision_tag = "^[a-zA-Z0-9-]{1,12}$" + // Will fail if var.provision_tag is invalid + regex_provision_tag = regex(local.regex_valid_provision_tag, var.provision_tag) == var.provision_tag ? 0 : "Variable [provision_tag] must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + + load_balancers_type_allowed_values = [ + "Network Load Balancer", + "Application Load Balancer" + ] + // Will fail if var.load_balancers_type is invalid + validate_load_balancers_type = index(local.load_balancers_type_allowed_values, var.load_balancers_type) + + lb_protocol_allowed_values = var.load_balancers_type == "Network Load Balancer" ? [ + "TCP", + "TLS", + "UDP", + "TCP_UDP" + ] : [ + "HTTP", + "HTTPS" + ] + // Will fail if var.load_balancer_protocol is invalid + validate_lb_protocol = index(local.lb_protocol_allowed_values, var.load_balancer_protocol) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_certificate = "^(arn:aws:[a-z]+::[0-9]{12}:server-certificate/[a-zA-Z0-9-]*)?$" + // Will fail if var.certificate is invalid + regex_certificate = regex(local.regex_valid_certificate, var.certificate) == var.certificate ? 0 : "Variable [certificate] must be a valid Amazon Resource Name (ARN), for example: arn:aws:iam::123456789012:server-certificate/web-server-certificate" + + regex_valid_service_port = "^([0-9]{1,4}|[1-5][0-9]{4}|6[0-4][0-9]{3}|65[0-4][0-9]{2}|655[0-2][0-9]|6553[0-5])?$" + // Will fail if var.service_port is invalid + regex_service_port = regex(local.regex_valid_service_port, var.service_port) == var.service_port ? 0 : "Custom service port must be a number between 0 and 65535" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash." + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters." + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash." + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR." + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses." + + regex_valid_server_ami = "^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$" + // Will fail if var.server_ami is invalid + regex_server_ami = regex(local.regex_valid_server_ami, var.server_ami) == var.server_ami ? 0 : "Amazon Machine Image ID must be in the form ami-xxxxxxxx or ami-xxxxxxxxxxxxxxxxx" + + alb_condition = var.load_balancers_type == "Application Load Balancer" + nlb_condition = var.load_balancers_type == "Network Load Balancer" + provided_port_condition = var.service_port != "" + encrypted_protocol_condition = (local.alb_condition && var.load_balancer_protocol == "HTTPS") || (local.nlb_condition && var.load_balancer_protocol == "TLS") ? true : false + deploy_management_condition = var.management_deploy == true + deploy_servers_condition = var.servers_deploy == true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale/main.tf b/deprecated/terraform/aws/R80.40/qs-autoscale/main.tf new file mode 100755 index 00000000..7fa5f27f --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale/main.tf @@ -0,0 +1,165 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +resource "aws_security_group" "external_alb_security_group" { + count = local.alb_condition ? 1 : 0 + description = "External ALB security group" + vpc_id = var.vpc_id + + egress { + from_port = local.encrypted_protocol_condition ? 9443 : 9080 + protocol = "tcp" + to_port = local.encrypted_protocol_condition ? 9443 : 9080 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + protocol = "tcp" + to_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + cidr_blocks = ["0.0.0.0/0"] + } +} + +module "external_load_balancer" { + source = "../modules/common/load_balancer" + + load_balancers_type = var.load_balancers_type + instances_subnets = var.gateways_subnets + prefix_name = "${var.prefix}-External" + internal = false + security_groups = local.alb_condition ? [aws_security_group.external_alb_security_group[0].id] : [] + tags = {} + vpc_id = var.vpc_id + load_balancer_protocol = var.load_balancer_protocol + target_group_port = local.encrypted_protocol_condition ? 9443 : 9080 + listener_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? "443" : "80" + certificate_arn = local.encrypted_protocol_condition ? var.certificate : "" + health_check_port = var.load_balancers_type == "Network Load Balancer" ? 8117 : null + health_check_protocol = var.load_balancers_type == "Network Load Balancer" ? "TCP" : null +} + +module "autoscale" { + source = "../autoscale" + providers = { + aws = aws + } + + prefix = var.prefix + asg_name = var.asg_name + vpc_id = var.vpc_id + subnet_ids = var.gateways_subnets + gateway_name = "${var.provision_tag}-security-gateway" + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + metadata_imdsv2_required = var.metadata_imdsv2_required + minimum_group_size = var.gateways_min_group_size + maximum_group_size = var.gateways_max_group_size + target_groups = tolist([module.external_load_balancer.target_group_arn]) + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding quickstart identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: autoscale_qs' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"autoscale_qs\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo -e '\nFinished Bootstrap script\n'" + management_server = "${var.provision_tag}-management" + configuration_template = "${var.provision_tag}-template" +} + +data "aws_region" "current"{} + +module "management" { + providers = { + aws = aws + } + count = local.deploy_management_condition ? 1 : 0 + source = "../management" + + vpc_id = var.vpc_id + subnet_id = var.gateways_subnets[0] + management_name = "${var.provision_tag}-management" + management_instance_type = var.management_instance_type + key_name = var.key_name + volume_encryption = var.enable_volume_encryption ? "alias/aws/ebs" : "" + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + iam_permissions = "Create with read-write permissions" + management_version = var.management_version + admin_shell = var.admin_shell + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + allow_upload_download = var.allow_upload_download + admin_cidr = var.admin_cidr + gateway_addresses = var.gateways_addresses + management_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding quickstart identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: management_qs' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"management_qs\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo 'Creating CME configuration'; autoprov_cfg -f init AWS -mn ${var.provision_tag}-management -tn ${var.provision_tag}-template -cn ${var.provision_tag}-controller -po ${var.gateways_policy} -otp ${var.gateway_SICKey} -r ${data.aws_region.current.name} -ver ${split("-", var.gateway_version)[0]} -iam; ${var.gateways_blades} && autoprov_cfg -f set template -tn ${var.provision_tag}-template -ips -appi -av -ab; echo -e '\nFinished Bootstrap script\n'" +} + +resource "aws_security_group" "internal_security_group" { + count = local.deploy_servers_condition ? 1 : 0 + vpc_id = var.vpc_id + + egress { + from_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + protocol = "tcp" + to_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = local.encrypted_protocol_condition ? 443 : 80 + protocol = "tcp" + to_port = local.encrypted_protocol_condition ? 443 : 80 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = -1 + protocol = "icmp" + to_port = -1 + cidr_blocks = ["0.0.0.0/0"] + } +} + +module "internal_load_balancer" { + count = local.deploy_servers_condition ? 1 : 0 + source = "../modules/common/load_balancer" + + load_balancers_type = var.load_balancers_type + instances_subnets = var.servers_subnets + prefix_name = "${var.prefix}-Internal" + internal = true + security_groups = local.alb_condition ? [aws_security_group.internal_security_group[0].id] : [] + tags = { + x-chkp-management = "${var.provision_tag}-management" + x-chkp-template = "${var.provision_tag}-template" + } + vpc_id = var.vpc_id + load_balancer_protocol = var.load_balancer_protocol + target_group_port = local.encrypted_protocol_condition ? 443 : 80 + listener_port = local.encrypted_protocol_condition ? "443" : "80" + certificate_arn = local.encrypted_protocol_condition ? var.certificate : "" +} + +module "custom_autoscale" { + count = local.deploy_servers_condition ? 1 : 0 + source = "../modules/custom-autoscale" + + prefix = var.prefix + asg_name = var.asg_name + vpc_id = var.vpc_id + servers_subnets = var.servers_subnets + server_ami = var.server_ami + server_name = "${var.provision_tag}-server" + servers_instance_type = var.servers_instance_type + key_name = var.key_name + servers_min_group_size = var.gateways_min_group_size + servers_max_group_size = var.gateways_max_group_size + servers_target_groups = module.internal_load_balancer[0].target_group_id + deploy_internal_security_group = local.nlb_condition ? true : false + source_security_group = local.nlb_condition ? "" : aws_security_group.internal_security_group[0].id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale/output.tf b/deprecated/terraform/aws/R80.40/qs-autoscale/output.tf new file mode 100755 index 00000000..edb1a1f6 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale/output.tf @@ -0,0 +1,45 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} + +output "management_name" { + value = "${var.provision_tag}-management" +} +output "internal_port" { + value = local.encrypted_protocol_condition ? 443 : 80 +} +output "load_balancer_url" { + value = module.external_load_balancer.load_balancer_url +} +output "external_load_balancer_arn" { + value = module.external_load_balancer.load_balancer_arn +} +output "internal_load_balancer_arn" { + value = module.internal_load_balancer[*].load_balancer_arn +} +output "external_lb_target_group_arn" { + value = module.external_load_balancer.target_group_arn +} +output "internal_lb_target_group_arn" { + value = module.internal_load_balancer[*].target_group_arn +} + +output "autoscale_autoscaling_group_name" { + value = module.autoscale.autoscale_autoscaling_group_name +} +output "autoscale_autoscaling_group_arn" { + value = module.autoscale.autoscale_autoscaling_group_arn +} +output "autoscale_security_group_id" { + value = module.autoscale.autoscale_security_group_id +} +output "autoscale_iam_role_name" { + value = module.autoscale.autoscale_iam_role_name +} + +output "configuration_template" { + value = "${var.provision_tag}-template" +} +output "controller_name" { + value = "${var.provision_tag}-controller" +} diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale/terraform.tfvars b/deprecated/terraform/aws/R80.40/qs-autoscale/terraform.tfvars new file mode 100755 index 00000000..d9eb16f4 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale/terraform.tfvars @@ -0,0 +1,48 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "TF" +asg_name = "asg-qs" + +// --- General Settings --- +vpc_id = "vpc-12345678" +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +provision_tag = "quickstart" +load_balancers_type = "Application Load Balancer" +load_balancer_protocol = "HTTP" +certificate = "" +service_port = "80" +admin_shell = "/etc/cli.sh" + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Web Servers Auto Scaling Group Configuration --- +servers_deploy = false +servers_subnets = ["subnet-1234abcd", "subnet-56789def"] +servers_instance_type = "t3.micro" +server_ami = "ami-12345678" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale/variables.tf b/deprecated/terraform/aws/R80.40/qs-autoscale/variables.tf new file mode 100755 index 00000000..070ec4f4 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale/variables.tf @@ -0,0 +1,231 @@ +// Module: Check Point CloudGuard Network Quick Start Auto Scaling +//Deploy a Check Point CloudGuard Network Security Gateways Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group. + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} +// --- General Settings --- +variable "vpc_id" { + type = string +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "provision_tag" { + type = string + description = "The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + default = "quickstart" +} +variable "load_balancers_type" { + type = string + description = "Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing" + default = "Network Load Balancer" +} +variable "load_balancer_protocol" { + type = string + description = "The protocol to use on the Load Balancer" +} +variable "certificate" { + type = string + description = "Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP" +} +variable "service_port" { + type = string + description = "The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS" +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateways_subnets" { + type = list(string) + description = "Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Web Servers Auto Scaling Group Configuration --- +variable "servers_deploy" { + type = bool + description = "Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored" + default = false +} +variable "servers_subnets" { + type = list(string) + description = "Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-1234,subnet-5678,subnet-9012)" +} +variable "servers_instance_type" { + type = string + description = "The EC2 instance type for the web servers" + default = "t3.micro" +} +module "validate_servers_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "server" + instance_type = var.servers_instance_type +} +variable "server_ami" { + type = string + description = "The Amazon Machine Image ID of a preconfigured web server (e.g. ami-1234)" +} diff --git a/deprecated/terraform/aws/R80.40/qs-autoscale/versions.tf b/deprecated/terraform/aws/R80.40/qs-autoscale/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/qs-autoscale/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/standalone-master/README.md b/deprecated/terraform/aws/R80.40/standalone-master/README.md new file mode 100755 index 00000000..fb6a5453 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone-master/README.md @@ -0,0 +1,201 @@ +# Check Point CloudGuard Network Security Management Server & Security Gateway (Standalone) Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation + +This solution uses the following modules: +- /terraform/aws/standalone +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/standalone-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/standalone: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/standalone: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/standalone-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/standalone-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + } + private_subnets_map = { + "us-east-1a" = 2 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + standalone_name = "Check-Point-Standalone-tf" + standalone_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + standalone_version = "R81.BYOL" + admin_shell = "/etc/cli.sh" + standalone_password_hash = "" + standalone_maintenance_mode_password_hash = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + standalone_hostname = "standalone-tf" + allow_upload_download = true + enable_cloudwatch = false + standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Standalone instance: + ``` + allocate_and_associate_eip = true + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| standalone_name | (Optional) The name tag of the Security Gateway & Management (Standalone) instance | string | n/a | Check-Point-Standalone-tf | no | +| standalone_instance_type | The instance type of the Security Gateway & Management (Standalone) instance | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance | map(string) | n/a | {} | no | +| standalone_version | Security Gateway & Management (Standalone) version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R81-BYOL
- R81-PAYG-NGTP
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R82-BYOL
- R82-PAYG-NGTP | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| standalone_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| standalone_hostname | (Optional) Security Gateway & Management (Standalone) prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| standalone_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| standalone_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|------------------------------|------------------------------------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| internal_rtb_id | The internal route table id | +| vpc_public_subnets_ids_list | A list of the public subnets ids | +| vpc_private_subnets_ids_list | A list of the private subnets ids | +| standalone_instance_id | The deployed Security Gateway & Management (Standalone) AWS instance id | +| standalone_instance_name | The deployed Security Gateway & Management (Standalone) AWS instance name | +| standalone_public_ip | The deployed Security Gateway & Management (Standalone) AWS public address | +| standalone_ssh | SSH command to the Security Gateway & Management (Standalone) | +| standalone_url | URL to the portal of the deployed Security Gateway & Management (Standalone) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231113 | Add support for BYOL license type for Standalone | +| 20231012 | Update AWS Terraform Provider version to 5.20.1 | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone-master/locals.tf b/deprecated/terraform/aws/R80.40/standalone-master/locals.tf new file mode 100755 index 00000000..61326301 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone-master/locals.tf @@ -0,0 +1,36 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_standalone_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.standalone_password_hash is invalid + regex_standalone_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_password_hash) == var.standalone_password_hash ? 0 : "Variable [standalone_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_maintenance_mode_password_hash) == var.standalone_maintenance_mode_password_hash ? 0 : "Variable [standalone_maintenance_mode_password_hash] must be a valid password hash" + +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone-master/main.tf b/deprecated/terraform/aws/R80.40/standalone-master/main.tf new file mode 100755 index 00000000..999c506e --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone-master/main.tf @@ -0,0 +1,63 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} + +module "launch_standalone_into_vpc" { + source = "../standalone" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_id = module.launch_vpc.public_subnets_ids_list[0] + private_subnet_id = module.launch_vpc.private_subnets_ids_list[0] + private_route_table = aws_route_table.private_subnet_rtb.id + resources_tag_name = var.resources_tag_name + standalone_name = var.standalone_name + standalone_instance_type = var.standalone_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + standalone_version = var.standalone_version + admin_shell = var.admin_shell + standalone_password_hash = var.standalone_password_hash + standalone_maintenance_mode_password_hash = var.standalone_maintenance_mode_password_hash + standalone_hostname = var.standalone_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + standalone_bootstrap_script = var.standalone_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + admin_cidr = var.admin_cidr + gateway_addresses = var.gateway_addresses +} diff --git a/deprecated/terraform/aws/R80.40/standalone-master/output.tf b/deprecated/terraform/aws/R80.40/standalone-master/output.tf new file mode 100755 index 00000000..11d557b9 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone-master/output.tf @@ -0,0 +1,27 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "internal_rtb_id" { + value = aws_route_table.private_subnet_rtb.id +} +output "vpc_public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "vpc_private_subnets_ids_list" { + value = module.launch_vpc.private_subnets_ids_list +} +output "standalone_instance_id" { + value = module.launch_standalone_into_vpc.standalone_instance_id +} +output "standalone_instance_name" { + value = module.launch_standalone_into_vpc.standalone_instance_name +} +output "standalone_public_ip" { + value = module.launch_standalone_into_vpc.standalone_public_ip +} +output "standalone_ssh" { + value = module.launch_standalone_into_vpc.standalone_ssh +} +output "standalone_url" { + value = module.launch_standalone_into_vpc.standalone_url +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/standalone-master/terraform.tfvars new file mode 100755 index 00000000..4f6b6131 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone-master/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 +} +private_subnets_map = { + "us-east-1a" = 2 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +standalone_name = "Check-Point-Standalone-tf" +standalone_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +standalone_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +standalone_password_hash = "" +standalone_maintenance_mode_password_hash = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +standalone_hostname = "standalone-tf" +allow_upload_download = true +enable_cloudwatch = false +standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone-master/variables.tf b/deprecated/terraform/aws/R80.40/standalone-master/variables.tf new file mode 100755 index 00000000..212dc108 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone-master/variables.tf @@ -0,0 +1,174 @@ +// Module: Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- EC2 Instance Configuration --- +variable "standalone_name" { + type = string + description = "(Optional) The name tag of the Security Gateway & Management (Standalone) instance" + default = "Check-Point-Standalone-tf" +} +variable "standalone_instance_type" { + type = string + description = "The instance type of the Security Gateway & Management (Standalone) instance" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "standalone" + instance_type = var.standalone_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "standalone_version" { + type = string + description = "Gateway & Management (Standalone) version and license" + default = "R81.20-BYOL" +} +module "validate_standalone_version" { + source = "../modules/common/version_license" + + chkp_type = "standalone" + version_license = var.standalone_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "standalone_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "standalone_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) The name tag of the resources" + default = "" +} +variable "standalone_hostname" { + type = string + description = "(Optional) Security Gateway & Management (Standalone) prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "standalone_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} diff --git a/deprecated/terraform/aws/R80.40/standalone-master/versions.tf b/deprecated/terraform/aws/R80.40/standalone-master/versions.tf new file mode 100755 index 00000000..a95f0172 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone/README.md b/deprecated/terraform/aws/R80.40/standalone/README.md new file mode 100755 index 00000000..e61e06ce --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/README.md @@ -0,0 +1,176 @@ +# Check Point CloudGuard Network Security Management Server & Security Gateway (Standalone) Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation + + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/standalone/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/standalone/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/standalone/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_id = "subnet-123456" + private_subnet_id = "subnet-345678" + private_route_table = "rtb-12345678" + + // --- EC2 Instance Configuration --- + standalone_name = "Check-Point-Standalone-tf" + standalone_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + standalone_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + standalone_password_hash = "" + standalone_maintenance_mode_password_hash = "" + // --- Advanced Settings --- + resources_tag_name = "tag-name" + standalone_hostname = "standalone-tf" + allow_upload_download = true + enable_cloudwatch = false + standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Standalone instance: + ``` + allocate_and_associate_eip = true + ``` + - To create route from '0.0.0.0/0' to the Standalone instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the Security Gateway & Management (Standalone) | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the Security Gateway & Management (Standalone) | string | n/a | n/a | yes | +| private_route_table | Sets '0.0.0.0/0' route to the Security Gateway & Management (Standalone) instance in the specified route table (e.g. rtb-12a34567) | string | n/a | "" | no | +| standalone_name | (Optional) The name tag of the Security Gateway & Management (Standalone) instance | string | n/a | Check-Point-Standalone-tf | no | +| standalone_instance_type | The instance type of the Security Gateway & Management (Standalone) instance | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance | map(string) | n/a | {} | no | +| standalone_version | Security Gateway & Management (Standalone) version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R81-BYOL
- R81-PAYG-NGTP
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R82-BYOL
- R82-PAYG-NGTP | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| standalone_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| standalone_hostname | (Optional) Security Gateway & Management (Standalone) prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| standalone_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| standalone_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|------------------------------------------------------------------------------| +| standalone_instance_id | The deployed Security Gateway & Management (Standalone) AWS instance id | +| standalone_instance_name | The deployed Security Gateway & Management (Standalone) AWS instance name | +| standalone_public_ip | The deployed Security Gateway & Management (Standalone) AWS public address | +| standalone_ssh | SSH command to the Security Gateway & Management (Standalone) | +| standalone_url | URL to the portal of the deployed Security Gateway & Management (Standalone) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231113 | Add support for BYOL license type for Standalone | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone/locals.tf b/deprecated/terraform/aws/R80.40/standalone/locals.tf new file mode 100755 index 00000000..6e438e83 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/locals.tf @@ -0,0 +1,41 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_standalone_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.standalone_password_hash is invalid + regex_standalone_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_password_hash) == var.standalone_password_hash ? 0 : "Variable [standalone_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_maintenance_mode_password_hash) == var.standalone_maintenance_mode_password_hash ? 0 : "Variable [standalone_maintenance_mode_password_hash] must be a valid password hash" + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.standalone_version), 0) + + standalone_bootstrap_script64 = base64encode(var.standalone_bootstrap_script) + standalone_password_hash_base64 = base64encode(var.standalone_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.standalone_maintenance_mode_password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone/main.tf b/deprecated/terraform/aws/R80.40/standalone/main.tf new file mode 100755 index 00000000..f9df43ff --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/main.tf @@ -0,0 +1,145 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.standalone_version + chkp_type = "standalone" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.standalone_name +} + +resource "aws_iam_instance_profile" "standalone_instance_profile" { + count = local.enable_cloudwatch_policy + path = "/" + role = aws_iam_role.standalone_iam_role[count.index].name +} + +resource "aws_iam_role" "standalone_iam_role" { + count = local.enable_cloudwatch_policy + assume_role_policy = data.aws_iam_policy_document.standalone_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "standalone_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + } +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_role.standalone_iam_role[count.index].name + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.standalone_name +} +resource "aws_network_interface" "public_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth0" + source_dest_check = false + tags = { + Name = format("%s-external-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.standalone_name) } +} +resource "aws_network_interface" "private_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth1" + source_dest_check = false + tags = { + Name = format("%s-internal-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.standalone_name) } +} + +module "common_eip" { + source = "../modules/common/elastic_ip" + + allocate_and_associate_eip = var.allocate_and_associate_eip + external_eni_id = aws_network_interface.public_eni.id + private_ip_address = aws_network_interface.public_eni.private_ip +} + +module "common_internal_default_route" { + source = "../modules/common/internal_default_route" + + private_route_table = var.private_route_table + internal_eni_id = aws_network_interface.private_eni.id +} + +resource "aws_launch_template" "standalone_launch_template" { + instance_type = var.standalone_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = (local.enable_cloudwatch_policy == 1 ? aws_iam_instance_profile.standalone_instance_profile[0].id : "") + } + + network_interfaces { + network_interface_id = aws_network_interface.public_eni.id + device_index = 0 + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.private_eni.id + device_index = 1 + } +} + +resource "aws_instance" "standalone-instance" { + launch_template { + id = aws_launch_template.standalone_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.standalone_name + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + user_data = templatefile("${path.module}/standalone_userdata.yaml", { + // script's arguments + Hostname = var.standalone_hostname, + PasswordHash = local.standalone_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + AdminSubnet = var.admin_cidr, + EnableInstanceConnect = var.enable_instance_connect, + StandaloneBootstrapScript = local.standalone_bootstrap_script64 + AllocateElasticIP = var.allocate_and_associate_eip + OsVersion = local.version_split + }) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone/output.tf b/deprecated/terraform/aws/R80.40/standalone/output.tf new file mode 100755 index 00000000..5a46d0fa --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/output.tf @@ -0,0 +1,15 @@ +output "standalone_instance_id" { + value = aws_instance.standalone-instance.id +} +output "standalone_instance_name" { + value = aws_instance.standalone-instance.tags["Name"] +} +output "standalone_public_ip" { + value = aws_instance.standalone-instance.public_ip +} +output "standalone_ssh" { + value = format("ssh -i %s admin@%s", var.key_name, aws_instance.standalone-instance.public_ip) +} +output "standalone_url" { + value = format("https://%s", aws_instance.standalone-instance.public_ip) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone/standalone_userdata.yaml b/deprecated/terraform/aws/R80.40/standalone/standalone_userdata.yaml new file mode 100755 index 00000000..1bdf7eca --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/standalone_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" installationType=\"standalone\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"standalone\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" adminSubnet=\"${AdminSubnet}\" allocatePublicAddress=\"${AllocateElasticIP}\" bootstrapScript64=\"${StandaloneBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone/terraform.tfvars b/deprecated/terraform/aws/R80.40/standalone/terraform.tfvars new file mode 100755 index 00000000..edad70cd --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/terraform.tfvars @@ -0,0 +1,39 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_id = "subnet-123456" +private_subnet_id = "subnet-345678" +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +standalone_name = "Check-Point-Standalone-tf" +standalone_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +standalone_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +standalone_password_hash = "" +standalone_maintenance_mode_password_hash = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +standalone_hostname = "standalone-tf" +allow_upload_download = true +enable_cloudwatch = false +standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/standalone/variables.tf b/deprecated/terraform/aws/R80.40/standalone/variables.tf new file mode 100755 index 00000000..afdec993 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/variables.tf @@ -0,0 +1,172 @@ +// Module: Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_id" { + type = string + description = "The public subnet of the Security Gateway & Management (Standalone)" +} +variable "private_subnet_id" { + type = string + description = "The private subnet of the Security Gateway & Management (Standalone)" +} +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Security Gateway & Management (Standalone) instance in the specified route table (e.g. rtb-12a34567)" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "standalone_name" { + type = string + description = "(Optional) The name tag of the Security Gateway & Management (Standalone) instance" + default = "Check-Point-Standalone-tf" +} +variable "standalone_instance_type" { + type = string + description = "The instance type of the Security Gateway & Management (Standalone) instance" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "standalone" + instance_type = var.standalone_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "standalone_version" { + type = string + description = "Security Gateway & Management (Standalone) version and license" + default = "R81.20-BYOL" +} +module "validate_standalone_version" { + source = "../modules/common/version_license" + + chkp_type = "standalone" + version_license = var.standalone_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "standalone_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "standalone_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) The name tag of the resources" + default = "" +} +variable "standalone_hostname" { + type = string + description = "(Optional) Security Gateway & Management (Standalone) prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "standalone_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} diff --git a/deprecated/terraform/aws/R80.40/standalone/versions.tf b/deprecated/terraform/aws/R80.40/standalone/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/standalone/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/tap/Check Point NOW onboarding page.docx b/deprecated/terraform/aws/R80.40/tap/Check Point NOW onboarding page.docx new file mode 100755 index 0000000000000000000000000000000000000000..54b4968d384d7f6e8725be4aa9cf35b497f5bf2f GIT binary patch literal 287849 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

gu0Stnz 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 z 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

wOvd~=X9sT|<9mLROS#)12cy7C(2xXkt& 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 literal 0 HcmV?d00001 diff --git a/deprecated/terraform/aws/R80.40/tap/CheckPoint_NOW_onboarding_page.pdf b/deprecated/terraform/aws/R80.40/tap/CheckPoint_NOW_onboarding_page.pdf new file mode 100755 index 0000000000000000000000000000000000000000..c25e9592852d07d2f26f9b9272632d2e81df42e9 GIT binary patch literal 390187 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 z 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

P5wTxfoWY5hy`Qldrt}vrvEV3s$u+_!FRU4 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\FZ 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 T`ui2#ZdWgy7u}Bkx$yr5?6R*5 literal 0 HcmV?d00001 diff --git a/deprecated/terraform/aws/R80.40/tap/README.md b/deprecated/terraform/aws/R80.40/tap/README.md new file mode 100755 index 00000000..bb2467ea --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tap/README.md @@ -0,0 +1,258 @@ +# Check Point Traffic Access Point (TAP) Terraform module for AWS + +Terraform module which deploys a TAP solution in an existing VPC on AWS. + +To learn about Check Point's TAP solution, click [here](CheckPoint_NOW_onboarding_page.pdf). + + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) - TAP Gateway +* [AWS CloudFormation Stack](https://www.terraform.io/docs/providers/aws/r/cloudformation_stack.html) - creates Traffic Mirror Filter and Target +* [AWS Lambdas](https://www.terraform.io/docs/providers/aws/r/lambda_function.html) - TAP Lambda, TAP Termination Lambda + +Learn more about [TAP Lambda](#TAP-Lambda) and [TAP Termination Lambda](#TAP-Termination-Lambda) + +This solution uses the following modules: +- /terraform/aws/modules/amis + + +## Prerequisites +* **Internet Gateway -** The VPC deployed into **must** have an [Internet Gateway](https://docs.aws.amazon.com/vpc/latest/userguide/VPC_Internet_Gateway.html) +configured as default route in the VPC's main route-table in order to allow communication between the TAP Gateway and Check Point NOW Cloud. +**Note:** Internet connectivity is mandatory pre-deployment. +* **License -** This module supports Check Point R80.40 NGTX-PAYG license only +* **NOW domain and Cyber Sentry -** +To create a NOW domain fill in the [NOW cloud registration form](https://now.checkpoint.com/register/index.html). +Once you are logged in to your NOW domain, create a Cyber Sentry and use its MAC address as the 'registration_key' variable in the terraform deployment. +For detailed information and instructions refer to the [NOW onboarding page](CheckPoint_NOW_onboarding_page.pdf). + +> **Note:** Make sure the Cyber Sentry you intend to connect to is 'decativated' pre-deployment in the NOW portal. + +### Notes and limitations +* As explained in [AWS Traffic Mirroring considerations](https://docs.aws.amazon.com/vpc/latest/mirroring/traffic-mirroring-considerations.html) page, +AWS supports traffic mirroring for [Nitro-based instance](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/instance-types.html#ec2-nitro-instances) only. +* Post-deployment refer to [Check Point NOW portal](https://now.checkpoint.com) > Cyber Sentries. +Once your Cyber sentry changes its state to 'activated' and 'connected' - the instance connected successfully to Check Point NOW Cloud. +This may take up to 20 minutes. +* Due to an AWS limitation the **maximum number of mirror sources per target** depends on the TAP Gateway instance type. +For a non-dedicated instance type as target, the limit is 10 sources. +For a dedicated instance type, the limit is 100 sources. +CGI supports the following dedicated instance types: c5.18xlarge and c5n.18xlarge +For more information please refer to [AWS Traffic Mirroring quotas and considerations](https://docs.aws.amazon.com/vpc/latest/mirroring/traffic-mirroring-considerations.html#traffic-mirroring-limits) page. + +## Note +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/tap/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +[Clone or download](https://github.com/CheckPointSW/CloudGuardIaaS) Check Point CloudGuard Network Github Repository. + +Configure your variables in /terraform/aws/tap/**terraform.tfvars** file as follows: +``` +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +external_subnet_id = "subnet-abc123" +internal_subnet_id = "subnet-def456" +resources_tag_name = "env1" + +// --- TAP Configuration --- +registration_key = "10:10:10:10:10:10" +vxlan_id = 10 +blacklist_tags = { + env = "staging" + state = "stable" +} +schedule_scan_interval = 60 + +// --- EC2 Instance Configuration --- +instance_name = "tap-gateway" +instance_type = "c5.xlarge" +key_name = "publickey" +``` +**main.tf** - Refers to the above configured variables and does not require any changes: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "tap" { + source = "../../modules/tap" + + // --- VPC Network Configuration --- + vpc_id = var.vpc_id + external_subnet_id = var.external_subnet_id + internal_subnet_id = var.internal_subnet_id + resources_tag_name = var.resources_tag_name + + // --- TAP Configuration --- + registration_key = var.registration_key + vxlan_id = var.vxlan_id + blacklist_tags = var.blacklist_tags + schedule_scan_interval = var.schedule_scan_interval + + // --- EC2 Instance Configuration --- + instance_name = var.instance_name + instance_type = var.instance_type + key_name = var.key_name +} +``` +From your tap directory's command line - +* Run 'terraform plan' to generate and show an execution plan +* Run 'terraform apply' to initiate deployment and build the TAP infrastructure +* Run 'terraform destroy' to destroy the terraform-managed infrastructure + +> Find Terraform commands doc [here](https://www.terraform.io/docs/commands/index.html). + +This module creates a Check Point TAP Gateway instance in the VPC specified by the user, +along with traffic mirror filter and target, and two lambda functions: TAP Lambda and TAP Termination Lambda. + +Once the Check Point TAP Gateway instance is deployed, the TAP Lambda is invoked and scans the entire +VPC for mirrorable NITRO instances. + +## Deployment + +First, purchase a [CloudGuard Network security gateway](https://aws.amazon.com/marketplace/pp/B07LB54LFB?qid=1586153579302&sr=0-2&ref_=srh_res_product_title) +with Threat Prevention & SandBlast from the AWS marketplace. +A named customer domain must be provisioned on the Check Point now.checkpoint.com SaaS – +during the Early Availability period, this must be performed by Check Point. +To create a NOW domain fill in the [NOW cloud registration form](https://now.checkpoint.com/register/index.html) and your request will be handled as soon as possible. +You will receive an email with a registration link – click that, and a certificate will be automatically generated and provided to you for download and import into your browser. +(Note: some browsers, e.g. Google Chrome, require a restart for the certificate to be activated – kill all instances of the browser, and restart it.) +Now point your browser at [now.checkpoint.com](https://now.checkpoint.com). You will be directed into your new domain. +Go to the Management > Sentries tab and click 'New' +* The New Sentry pane will open – select 'Virtual’, enter an optional description, verify the time zone, and click ADD +* A new sentry entry will appear. It will be uniquely identified by automatically generated 'Name’ and 'MAC Address’ +* Download the CloudGuard Network TAP Terraform module from [CloudGuard Network Github - TAP module](https://github.com/CheckPointSW/CloudGuardIaaS/tree/master/terraform/aws/modules/tap). +Edit terraform.tfvars file according to the instructions in the [Usage](#Usage) section above, using the sentry’s 'MAC Address’ for the registration_key variable. +* Launch the module using Terraform. As described above, this module creates a Check Point TAP Gateway instance in the VPC specified by the user, along with traffic mirror filter and target, and two lambda functions: 'TAP Lambda' and 'TAP Termination Lambda'. Once the Check Point CloudGuard Network TAP Gateway instance is deployed, the TAP Lambda is invoked and scans the entire VPC for mirrorable NITRO instances that meet the configured selection criteria. +* After up to 20 minutes, the sentry state will change to “Connected” in the NOW portal. +Check the Logs tab to see that network traffic is flowing into the sentry. + +### TAP Lambda + +#### IAM role +The module creates an IAM role for the TAP Lambda, named 'chkp_iam_tap_lambda' suffixed with a uuid. +This role is granted minimum permissions for the Lambda to execute. + +#### Responsibilities + +1. Invoked by Terraform once the Check Point TAP Gateway instance is deployed. + 1. Scans the VPC for mirrorable instances + 2. Creates traffic mirror sessions between the TAP Gateway traffic mirror target + and the primary ENI of non-blacklisted instances + 3. Skips traffic mirror session creation for blacklisted instances + +2. Invoked by an EC2 event: Every instance in the VPC that changes its state to 'Running'. + 1. Updates TAP for triggered instance - If not blacklisted and not TAPed, + creates traffic mirror session to the TAP Gateway traffic mirror target. + If blacklisted and TAPed, deletes traffic mirror session with the TAP Gateway target + 2. Scans VPC and updates TAP for all mirrorable instances (see 2.i) + +3. Invoked by a scheduled event: every X minutes, configured by the 'schedule_scan_interval' variable (default = 60). + 1. Scans the VPC for mirrorable instances + 2. Updates TAP for all mirrorable instances in the VPC (see 2.i) + + +#### Instances blacklisting: + +This module supports tag based blacklist mechanism to avoid TAP for desired instances. + +The Terraform TAP module holds a 'blacklist_tags' variable of type map(string). +The 'blacklist_tags' variable consists of key value pairs representing tag-key and tag-value pairs. + +The TAP Lambda will create traffic mirror sessions only for instances which **do not** hold any of +these tag pairs. Instances with any of these tag pairs will not be TAPed by the TAP Lambda function. +If a blacklisted instance is already TAPed, the TAP Lambda will act accordingly and +delete the traffic mirror session. + +During the solution deployment, the 'blacklist_tags' variable's values are joined to a string in the +following structure: "key1=value1:key2-value2:key3=value3" and so on. +This string is passed as 'TAP_BLACKLIST' environment variable to the TAP Lambda. +You can update the blacklist tags list by editing the TAP Lambda 'TAP_BLACKLIST' environment variable. +The structure "key1=value1:key2-value2:key3=value3" of the variable must be maintained. + + +### TAP Termination Lambda + + This Lambda should be manually invoked **prior** to destroying the Terraform environment. + The environment destruction **will fail** if skipping the Termination Lambda invocation. + +#### IAM role +The module creates an IAM role for the TAP Termination Lambda, named 'chkp_iam_tap_termination_lambda' suffixed with a uuid. +This role is granted minimum permissions for the Lambda to execute. + +#### Responsibilities: + +Lambda deletes all traffic mirror sessions associated with the TAP Gateway's target. +This step is crucial before environment destruction in order for destruction to finish successfully +(an alternative way is to navigate to AWS traffic mirror sessions page and manually +delete the relevant sessions). + + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------|-----------------------------------------------------------------------------------------------------|-------------|----------------|-------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| external_subnet_id | The external subnet of the security gateway (internet access) | string | n/a | n/a | yes | +| internal_subnet_id | The internal subnet of the security gateway. This subnet will be connected to the mirrored sources. | string | n/a | n/a | yes | +| resources_tag_name | (Optional) Resources prefix tag | string | n/a | "" | no | +| registration_key | The gateway registration key to Check Point NOW cloud | string | n/a | n/a | yes | +| vxlan_id | (Optional) VXLAN ID (number) for mirroring sessions | number | n/a | 1 | no | +| blacklist_tags | Key value pairs of tag key and tag value. Instances with any of these tag pairs will not be TAPed | map(string) | n/a | {} | no | +| schedule_scan_interval | (minutes) Lambda will scan the VPC every X minutes for TAP updates | number | n/a | 60 | no | +| instance_name | AWS instance name to launch | string | n/a | CP-TAP-Gateway-tf | no | +| instance_type | AWS instance type - View [Notes and limitations](#Notes-and-limitations) section | string | n/a | c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | + + +## Outputs +| Name | Description | +|--------------------------------|------------------------------------------------------------------------------------------------------------------------------------------| +| tap-gateway_instance_id | The instance id of the deployed Check Point TAP Gateway | +| gateway_instance_name | The instance name of the deployed Check Point TAP Gateway | +| gateway_instance_public_ip | The public ip address of the deployed Check Point TAP Gateway | +| traffic_mirror_filter_id | The traffic mirror filter id created during deployment by the 'tap_target_and_filter' stack | +| traffic_mirror_target_id | The traffic mirror target id pointing to the TAP Gateway's internal ENI - created during deployment by the 'tap_target_and_filter' stack | +| tap_lambda_name | TAP main lambda name (responsible for creating and deleting traffic mirror sessions with the TAP Gateway's target) | +| tap_lambda_description | TAP main lambda description | +| termination_lambda_name | TAP termination lambda name (deletes all traffic mirror sessions with the TAP Gateway's target) | +| termination_lambda_description | TAP termination lambda description | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|----------------------------------------------------------------------------------| +| 20210329 | Stability fixes | +| 20210309 | AWS Terraform modules refactor | +| 20200413 | First release of Check Point Traffic Access Point (TAP) Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/tap/main.tf b/deprecated/terraform/aws/R80.40/tap/main.tf new file mode 100755 index 00000000..01cc19d0 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tap/main.tf @@ -0,0 +1,301 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.version_license + chkp_type = "gateway" +} + +resource "aws_security_group" "tap_sg" { + description = format("%s Security group", var.resources_tag_name != "" ? var.resources_tag_name : var.instance_name) + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + protocol = "tcp" + from_port = 443 + to_port = 443 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + protocol = "tcp" + from_port = 22 + to_port = 22 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + description = "allow VXLAN for traffic mirroring" + protocol = "udp" + from_port = 4789 + to_port = 4789 + cidr_blocks = ["0.0.0.0/0"] + } + name = format("%s_SecurityGroup", var.resources_tag_name != "" ? var.resources_tag_name : var.instance_name) // Group name + tags = { + Name = format("%s_SecurityGroup", var.resources_tag_name != "" ? var.resources_tag_name : var.instance_name) // Resource name + } +} +resource "aws_network_interface" "external-eni" { + subnet_id = var.external_subnet_id + security_groups = [aws_security_group.tap_sg.id] + description = "eth0" + source_dest_check = false + tags = { + Name = format("%s-external_network_interface", var.resources_tag_name != "" ? var.resources_tag_name : var.instance_name) + } +} +resource "aws_network_interface" "internal-eni" { + subnet_id = var.internal_subnet_id + security_groups = [aws_security_group.tap_sg.id] + description = "eth1" + source_dest_check = false + tags = { + Name = format("%s-internal_network_interface", var.resources_tag_name != "" ? var.resources_tag_name : var.instance_name) + } +} +resource "aws_eip" "eip" { + network_interface = aws_network_interface.external-eni.id +} +resource "aws_instance" "tap_gateway" { + depends_on = [ + aws_network_interface.external-eni, + aws_network_interface.internal-eni, + aws_eip.eip + ] + + ami = module.amis.ami_id + tags = { + Name = var.instance_name + } + instance_type = var.instance_type + key_name = var.key_name + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = 100 + } + network_interface { + // external + network_interface_id = aws_network_interface.external-eni.id + device_index = 0 + } + network_interface { + // internal + network_interface_id = aws_network_interface.internal-eni.id + device_index = 1 + } + + user_data = templatefile("${path.module}/tap_user_data.sh", { + // script's arguments + RegistrationKey = var.registration_key + VxlanIds = var.vxlan_id + }) +} + +// Create CloudFormation Stack +resource "random_id" "stack_uuid" { + byte_length = 5 +} +resource "aws_cloudformation_stack" "tap_target_and_filter" { + depends_on = [aws_instance.tap_gateway] + name = format("traffic-mirror-filter-and-target-%s", random_id.stack_uuid.hex) + + parameters = { + MirroringNetworkInterfaceId = aws_network_interface.internal-eni.id + EnvironmentPrefix = var.resources_tag_name + } + template_url = "https://cgi-cfts.s3.amazonaws.com/utils/tap_target_and_filter.yaml" +} +locals { + trafficMirrorTargetId = aws_cloudformation_stack.tap_target_and_filter.outputs["TrafficMirrorTargetId"] + trafficMirrorFilterId = aws_cloudformation_stack.tap_target_and_filter.outputs["TrafficMirrorFilterId"] +} + +// Lambdas +// --- TAP Lambda --- +data "aws_iam_policy_document" "assume_policy_doc" { + statement { + effect = "Allow" + principals { + identifiers = ["lambda.amazonaws.com"] + type = "Service" + } + actions = ["sts:AssumeRole"] + } +} +data "aws_iam_policy_document" "tap_lambda_policy_doc" { + statement { + effect = "Allow" + actions = [ + "logs:CreateLogGroup", + "logs:CreateLogStream", + "logs:PutLogEvents", + "ec2:DescribeInstances", + "ec2:CreateTags", + "ec2:DeleteTrafficMirrorSession", + "ec2:CreateTrafficMirrorSession", + "ec2:DescribeTrafficMirrorSessions" + ] + resources = ["*"] + } +} +resource "aws_iam_role" "tap_lambda_iam_role" { + name_prefix = "chkp_iam_tap_lambda" + assume_role_policy = data.aws_iam_policy_document.assume_policy_doc.json +} +resource "aws_iam_role_policy" "tap_lambda_policy" { + policy = data.aws_iam_policy_document.tap_lambda_policy_doc.json + role = aws_iam_role.tap_lambda_iam_role.id +} +// Lambda Function +resource "random_id" "tap_lambda_uuid" { + byte_length = 5 +} +data "archive_file" "tap_lambda_zip" { + type = "zip" + source_file = "${path.module}/tap_lambda.py" + output_path = "${path.module}/tap_lambda.zip" +} +locals { + blacklisted_tag_pairs_joined = join(":", [for tag_key in keys(var.blacklist_tags): join("=", [tag_key, var.blacklist_tags[tag_key]])]) +} +resource "aws_lambda_function" "tap_lambda" { + depends_on = [aws_instance.tap_gateway] + function_name = format("chkp_tap_lambda-%s", random_id.tap_lambda_uuid.hex) + description = "The TAP lambda creates traffic mirror sessions with the TAP gateway instance, and removes them for blacklisted instances in the VPC." + + filename = "${path.module}/tap_lambda.zip" + + role = aws_iam_role.tap_lambda_iam_role.arn + handler = "tap_lambda.lambda_handler" + runtime = "python3.8" + timeout = 30 + + environment { + variables = { + VPC_ID = var.vpc_id + GW_ID = aws_instance.tap_gateway.id + TM_TARGET_ID = local.trafficMirrorTargetId + TM_FILTER_ID = local.trafficMirrorFilterId + VNI = var.vxlan_id + TAP_BLACKLIST = local.blacklisted_tag_pairs_joined + } + } +} +// CloudWatch event - EC2 state change to Running +resource "aws_cloudwatch_event_rule" "on_ec2_running_state" { + name_prefix = "tap_ec2_running_rule" + description = "Invoked when an instance changes its state to Running" + event_pattern = </var/log/aws-user-data.log 2>&1 + +echo template_name: TAP_tf >> /etc/cloud-version +echo template_version: 20210309 >> /etc/cloud-version +echo template_type: terraform >> $cv_path + +hname="CP-TAP" + +echo "Generating SIC password" +sic=$(tr -dc "0-9a-zA-Z" < /dev/urandom | head -c 8) + +blink_config -s "hostname='$hname'&gateway_cluster_member=false&ftw_sic_key='$sic'&upload_info=true&download_info=true" +rc=$? + +echo "Pulling NOW install script..." +INSTALLER=/var/log/now_installer + +runtime="10 minute" +endtime=$(date -ud "$runtime" +%s) + +while [[ $(date -u +%s) -le $endtime ]]; do + curl_cli -s -S --cacert "$CPDIR/conf/ca-bundle.crt" https://portal.now.checkpoint.com/static/configure.aws.sh -o $INSTALLER && break + sleep 2 +done + +chmod +x $INSTALLER +dos2unix $INSTALLER +$INSTALLER ${RegistrationKey} ${VxlanIds} >& $FWDIR/log/now_installer.elg + +LOADER=$FWDIR/bin/loadInstaller +echo '' > $LOADER +chmod +x "$LOADER" + +cpwd_admin start -name NOW_HF_LOADER -path "$LOADER" -command loadInstaller -slp_timeout 5 -retry_limit 10 +echo "done" diff --git a/deprecated/terraform/aws/R80.40/tap/terraform.tfvars b/deprecated/terraform/aws/R80.40/tap/terraform.tfvars new file mode 100755 index 00000000..f6fbebcb --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tap/terraform.tfvars @@ -0,0 +1,21 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +external_subnet_id = "subnet-abc123" +internal_subnet_id = "subnet-def456" +resources_tag_name = "env1" + +// --- TAP Configuration --- +registration_key = "10:10:10:10:10:10" +vxlan_id = 10 +blacklist_tags = { + env = "staging" + state = "stable" +} +schedule_scan_interval = 60 + +// --- EC2 Instance Configuration --- +instance_name = "tap-gateway" +instance_type = "c5.xlarge" +key_name = "publickey" diff --git a/deprecated/terraform/aws/R80.40/tap/variables.tf b/deprecated/terraform/aws/R80.40/tap/variables.tf new file mode 100755 index 00000000..e7e45a6d --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tap/variables.tf @@ -0,0 +1,89 @@ +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "external_subnet_id" { + type = string + description = "The external subnet of the security gateway (internet access)" +} +variable "internal_subnet_id" { + type = string + description = "The internal subnet of the security gateway. This subnet will be connected to the mirrored sources." +} +variable "resources_tag_name" { + type = string + description = "(Optional) Resources prefix tag" + default = "" +} + +// --- TAP Configuration --- +variable "registration_key" { + type = string + description = "The gateway registration key to Check Point NOW cloud" +} +variable "vxlan_id" { + type = number + description = "(Optional) VXLAN ID (number) for mirroring sessions - Predefined VTEP number" + default = 1 +} +variable "blacklist_tags" { + type = map(string) + description = "Key value pairs of tag key and tag value. Instances with any of these tag pairs will not be TAPed" + default = {} +} +variable "schedule_scan_interval" { + type = number + description = "(minutes) Lambda will scan the VPC every X minutes for TAP updates" + default = 60 +} + +// --- EC2 Instance Configuration --- +variable "instance_name" { + type = string + description = "AWS instance name to launch" + default = "CP-TAP-Gateway-tf" +} +variable "instance_type" { + type = string + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} + +// --- Check Point Settings --- +variable "version_license" { + type = string + description = "version and license" + default = "R80.40-PAYG-NGTX" +} +module "validate_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.version_license +} diff --git a/deprecated/terraform/aws/R80.40/tests/cluster_master_test.go b/deprecated/terraform/aws/R80.40/tests/cluster_master_test.go new file mode 100755 index 00000000..adf31fe9 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/cluster_master_test.go @@ -0,0 +1,100 @@ +package tests + +import ( + "github.com/stretchr/testify/assert" + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" +) + +// Test the Terraform module in aws/cluster-master using terratest. +func TestClusterMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsClusterMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetClusterMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsClusterMaster(t, terraformOptions) +} + +func GetTerraformOptionsClusterMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../cluster-master", + + // Variables passed to the module execution using -var options. To change any value refer to globals.go + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMapSingle, + "private_subnets_map": privateSubnetsMapSingle, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": clusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "allocate_and_associate_eip": allocateAndAssociatePublicEip, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueClusterGateway}, + "predefined_role": predefinedRole, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "memberAToken": gatewaySmart1CloudToken, + "memberBToken": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetClusterMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsClusterMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsClusterMaster(t *testing.T, terraformOptions *terraform.Options) { + outputAmiId := terraform.Output(t, terraformOptions, "ami_id") + outputClusterPublicIP := terraform.Output(t, terraformOptions, "cluster_public_ip") + outputMemberAEipPublicIP := terraform.Output(t, terraformOptions, "member_a_public_ip") + outputMemberBEipPublicIP := terraform.Output(t, terraformOptions, "member_b_public_ip") + outputMemberASSH := terraform.Output(t, terraformOptions, "member_a_ssh") + outputMemberBSSH := terraform.Output(t, terraformOptions, "member_b_ssh") + outputMemberAURL := terraform.Output(t, terraformOptions, "member_a_url") + outputMemberBURL := terraform.Output(t, terraformOptions, "member_b_url") + + assert.NotEmpty(t, outputAmiId) + assert.NotEmpty(t, outputClusterPublicIP) + assert.NotEmpty(t, outputMemberAEipPublicIP) + assert.NotEmpty(t, outputMemberBEipPublicIP) + assert.NotEmpty(t, outputMemberASSH) + assert.NotEmpty(t, outputMemberBSSH) + assert.NotEmpty(t, outputMemberAURL) + assert.NotEmpty(t, outputMemberBURL) +} diff --git a/deprecated/terraform/aws/R80.40/tests/cross_az_cluster_master_test.go b/deprecated/terraform/aws/R80.40/tests/cross_az_cluster_master_test.go new file mode 100755 index 00000000..9e09bcef --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/cross_az_cluster_master_test.go @@ -0,0 +1,99 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" + "testing" +) + +// Test the Terraform module in aws/cross-az-cluster-master using terratest. +func TestCrossAzClusterMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsCrossAzClusterMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetCrossAzClusterMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsCrossAzClusterMaster(t, terraformOptions) +} + +func GetTerraformOptionsCrossAzClusterMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../cross-az-cluster-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "private_subnets_map": privateSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": crossAZClusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueClusterGateway}, + "predefined_role": predefinedRole, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "memberAToken": gatewaySmart1CloudToken, + "memberBToken": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetCrossAzClusterMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsCrossAzClusterMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsCrossAzClusterMaster(t *testing.T, terraformOptions *terraform.Options) { + outputAmiId := terraform.Output(t, terraformOptions, "ami_id") + outputClusterPublicIP := terraform.Output(t, terraformOptions, "cluster_public_ip") + outputMemberAPublicIP := terraform.Output(t, terraformOptions, "member_a_public_ip") + outputMemberBPublicIP := terraform.Output(t, terraformOptions, "member_b_public_ip") + outputMemberASSH := terraform.Output(t, terraformOptions, "member_a_ssh") + outputMemberBSSH := terraform.Output(t, terraformOptions, "member_b_ssh") + outputMemberAURL := terraform.Output(t, terraformOptions, "member_a_url") + outputMemberBURL := terraform.Output(t, terraformOptions, "member_b_url") + + // Validate that all output values exist + assert.NotEmpty(t, outputAmiId) + assert.NotEmpty(t, outputClusterPublicIP) + assert.NotEmpty(t, outputMemberAPublicIP) + assert.NotEmpty(t, outputMemberASSH) + assert.NotEmpty(t, outputMemberAURL) + assert.NotEmpty(t, outputMemberBPublicIP) + assert.NotEmpty(t, outputMemberBSSH) + assert.NotEmpty(t, outputMemberBURL) +} diff --git a/deprecated/terraform/aws/R80.40/tests/gateway_master_test.go b/deprecated/terraform/aws/R80.40/tests/gateway_master_test.go new file mode 100755 index 00000000..dd803d59 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/gateway_master_test.go @@ -0,0 +1,119 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/aws" + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/gateway-master using terratest. +func TestGatewayMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsGatewayMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetGatewayMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsGatewayMaster(t, terraformOptions) +} + +func GetTerraformOptionsGatewayMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../gateway-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMapSingle, + "private_subnets_map": privateSubnetsMapSingle, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": gatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "allocate_and_associate_eip": allocateAndAssociatePublicEip, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueGateway}, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "gateway_TokenKey": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + + "control_gateway_over_public_or_private_address": gatewaysProvisionAddressType, + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetGatewayMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsGatewayMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsGatewayMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputInternalRouteTableId := terraform.Output(t, terraformOptions, "internal_rtb_id") + outputVpcPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_public_subnets_ids_list") + outputVpcPrivateSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_private_subnets_ids_list") + outputAmiId := terraform.Output(t, terraformOptions, "ami_id") + outputPermissiveSgId := terraform.Output(t, terraformOptions, "permissive_sg_id") + outputPermissiveSgName := terraform.Output(t, terraformOptions, "permissive_sg_name") + outputGatewayUrl := terraform.Output(t, terraformOptions, "gateway_url") + outputGatewayPublicIp := terraform.Output(t, terraformOptions, "gateway_public_ip") + outputGatewayInstanceId := terraform.Output(t, terraformOptions, "gateway_instance_id") + outputGatewayInstanceName := terraform.Output(t, terraformOptions, "gateway_instance_name") + + instanceTags := aws.GetTagsForEc2Instance(t, region, outputGatewayInstanceId) + nameTag, containsNameTag := instanceTags["Name"] + assert.True(t, containsNameTag) + assert.Equal(t, gatewayExpectedName, nameTag) + assert.Equal(t, gatewayExpectedName, outputGatewayInstanceName) + + testTag, containsTestTag := instanceTags[expectedTestTagKey] + assert.True(t, containsTestTag) + assert.Equal(t, expectedTestTagValueGateway, testTag) + + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputInternalRouteTableId) + assert.NotEmpty(t, outputVpcPublicSubnetsIdsList) + assert.NotEmpty(t, outputVpcPrivateSubnetsIdsList) + assert.NotEmpty(t, outputAmiId) + assert.NotEmpty(t, outputPermissiveSgId) + assert.NotEmpty(t, outputPermissiveSgName) + assert.NotEmpty(t, outputGatewayUrl) + assert.NotEmpty(t, outputGatewayPublicIp) + assert.NotEmpty(t, outputGatewayInstanceId) + assert.NotEmpty(t, outputGatewayInstanceName) +} diff --git a/deprecated/terraform/aws/R80.40/tests/globals.go b/deprecated/terraform/aws/R80.40/tests/globals.go new file mode 100755 index 00000000..647a026f --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/globals.go @@ -0,0 +1,177 @@ +package tests + +import "fmt" + +// AWS region for deployed resources +const region = "ca-central-1" + +var envVars = map[string]string{ + "AWS_DEFAULT_REGION": region, +} + +const availabilityZoneA = region + "a" + +const availabilityZoneB = region + "b" + +// Predefined prefix for deployed resources +const predefinedPrefix = "test" + +// Predefined names for deployed resources +const gatewayPredefinedName = "CheckPoint-Gateway" + +const standalonePredefinedName = "CheckPoint-Standalone" + +const managementPredefinedName = "CheckPoint-Management" + +const gwlbPredefinedName = "CheckPoint-GWLB" + +const clusterGatewayPredefinedName = "CheckPoint-Cluster-Gateway" + +const crossAZClusterGatewayPredefinedName = "CheckPoint-Cross-AZ-Cluster-Gateway" + +const qsAutoscaleGatewayPredefinedName = "quickstart-security-gateway" + +const qsAutoscaleProvisionTag = "quickstart" + +const configurationTemplate = "configuration-template" + +// Expected names for deployed resources +func getExpectedName(predefinedName string) string { + return fmt.Sprintf("%s-%s", predefinedPrefix, predefinedName) +} + +var gatewayExpectedName = getExpectedName(gatewayPredefinedName) + +var standaloneExpectedName = getExpectedName(standalonePredefinedName) + +var managementExpectedName = getExpectedName(managementPredefinedName) + +var gwlbExpectedName = getExpectedName(gwlbPredefinedName) + +var clusterGatewayExpectedName = getExpectedName(clusterGatewayPredefinedName) + +var crossAZClusterGatewayExpectedName = getExpectedName(crossAZClusterGatewayPredefinedName) + +var qsAutoscaleGatewayExpectedName = getExpectedName(qsAutoscaleGatewayPredefinedName) + +// Autoscale group capacity configuration +const autoscaleGroupExpectedCapacityMin = 1 + +const autoscaleGroupExpectedCapacityMax = 1 + +const targetGroup1Name = "tf-test-target-group-1" + +// Common parameters for deployed resources +const keyName = "tf-test" + +const version = "R81.20-BYOL" + +const standaloneVersion = "R81.20-BYOL" + +const adminShell = "/bin/bash" + +const gatewayBootstrapScript = "echo 'this is gateway bootstrap script' > /home/admin/bootstrap.txt" + +const standaloneBootstrapScript = "echo 'this is standalone bootstrap script' > /home/admin/bootstrap.txt" + +const passwordHash = "12345678" + +const SICKey = "12345678" + +const gatewayInstanceType = "c5.xlarge" + +const standaloneInstanceType = gatewayInstanceType + +const managementInstanceType = "m5.xlarge" + +const volumeSize = 100 + +const volumeEncryption = "alias/aws/ebs" + +const webServerInstanceType = "t3.micro" + +const webServerAMI = "ami-0718a739967397e7d" + +const volumeType = "gp3" + +const anywhereAddress = "0.0.0.0/0" + +const loadBalancersType = "Network Load Balancer" + +const loadBalancerProtocol = "TCP" + +const certificate = "" + +const servicePort = "80" + +const enableVolumeEncryption = true + +const allocatePublicIP = true + +const allocateAndAssociatePublicEip = true + +const allowUploadDownload = true + +const enableInstanceConnect = true + +const enableCloudWatch = false + +const connectionAcceptanceRequired = false + +const enableCrossZoneLoadBalancing = true + +const managementDeploy = true + +const webServerDeploy = true + +const gatewaysBlades = true + +const disableInstanceTermination = false + +const gatewaySmart1CloudToken = "" + +const predefinedRole = "" + +const primaryNtp = "" + +const secondaryNtp = "" + +const expectedTestTagKey = "test_tag" + +const expectedTestTagValueClusterGateway = "cluster_gateway_tf" + +const expectedTestTagValueGateway = "gateway_tf" + +const autoscaleGroupName = "CheckPoint-ASG" + +const resourcesTagName = "tag-name" + +const gatewayHostname = "gw-hostname" + +const gatewaysProvisionAddressType = "private" + +const gatewaysPolicy = "Standard" + +const gatewayManagement = "Locally managed" + +// New VPC configuration +const vpcCIDR = "10.0.0.0/16" + +var publicSubnetsMap = map[string]int{availabilityZoneA: 1, availabilityZoneB: 3} + +var privateSubnetsMap = map[string]int{availabilityZoneA: 2, availabilityZoneB: 4} + +var publicSubnetsMapSingle = map[string]int{availabilityZoneA: 1} + +var privateSubnetsMapSingle = map[string]int{availabilityZoneA: 2} + +var tgwSubnetsMap = map[string]int{availabilityZoneA: 5, availabilityZoneB: 6} + +var availabilityZones = []string{availabilityZoneA, availabilityZoneB} + +const numberOfAZs = 2 + +const subnetsBitLength = 8 + +// Controller expected names +const gwlbControlllerExpectedName = "gwlb-controller" diff --git a/deprecated/terraform/aws/R80.40/tests/gwlb_master_test.go b/deprecated/terraform/aws/R80.40/tests/gwlb_master_test.go new file mode 100755 index 00000000..787277a8 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/gwlb_master_test.go @@ -0,0 +1,99 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/gwlb-master using terratest. +func TestGwlbMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsGwlbMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsGwlbMaster(t, terraformOptions) +} + +func GetTerraformOptionsGwlbMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../gwlb-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "volume_size": volumeSize, + "enable_instance_connect": enableInstanceConnect, + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + "admin_shell": adminShell, + + "gateway_load_balancer_name": gwlbExpectedName, + "target_group_name": targetGroup1Name, + "connection_acceptance_required": connectionAcceptanceRequired, + "enable_cross_zone_load_balancing": enableCrossZoneLoadBalancing, + + "gateway_name": gatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "minimum_group_size": autoscaleGroupExpectedCapacityMin, + "maximum_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "gateways_provision_address_type": gatewaysProvisionAddressType, + "allocate_public_IP": allocatePublicIP, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "gateways_policy": gatewaysPolicy, + "gateway_management": gatewayManagement, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + + "volume_type": volumeType, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsGwlbMaster(t *testing.T, terraformOptions *terraform.Options) { + outputDeployment := terraform.Output(t, terraformOptions, "Deployment") + outputManagementPublicIP := terraform.Output(t, terraformOptions, "management_public_ip") + outputGWLBARN := terraform.Output(t, terraformOptions, "gwlb_arn") + outputGWLBServiceName := terraform.Output(t, terraformOptions, "gwlb_service_name") + outputGWLBName := terraform.Output(t, terraformOptions, "gwlb_name") + outputGWLBControllerName := terraform.Output(t, terraformOptions, "controller_name") + outputConfigurationTemplateName := terraform.Output(t, terraformOptions, "template_name") + + assert.Equal(t, outputGWLBName, gwlbExpectedName) + assert.Equal(t, outputGWLBControllerName, gwlbControlllerExpectedName) + assert.Equal(t, outputConfigurationTemplateName, configurationTemplate) + + assert.NotEmpty(t, outputDeployment) + assert.NotEmpty(t, outputManagementPublicIP) + assert.NotEmpty(t, outputGWLBARN) + assert.NotEmpty(t, outputGWLBServiceName) +} diff --git a/deprecated/terraform/aws/R80.40/tests/qs_autoscale_master_test.go b/deprecated/terraform/aws/R80.40/tests/qs_autoscale_master_test.go new file mode 100755 index 00000000..df2bdbab --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/qs_autoscale_master_test.go @@ -0,0 +1,129 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/aws" + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in qs-autoscale-master using terratest. +func TestQsAutoscaleMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsQsAutoscaleMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsQsAutoscaleMaster(t, terraformOptions) +} + +func GetTerraformOptionsQsAutoscaleMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../qs-autoscale-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "prefix": predefinedPrefix, + "asg_name": autoscaleGroupName, + + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "private_subnets_map": privateSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "allow_upload_download": allowUploadDownload, + "provision_tag": qsAutoscaleProvisionTag, + + "load_balancers_type": loadBalancersType, + "load_balancer_protocol": loadBalancerProtocol, + "certificate": certificate, + "service_port": servicePort, + + "gateway_instance_type": gatewayInstanceType, + "gateways_min_group_size": autoscaleGroupExpectedCapacityMin, + "gateways_max_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "enable_cloudwatch": enableCloudWatch, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "gateways_policy": gatewaysPolicy, + "gateways_blades": gatewaysBlades, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + + "servers_deploy": webServerDeploy, + "servers_instance_type": webServerInstanceType, + "server_ami": webServerAMI, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsQsAutoscaleMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "public_subnets_ids_list") + outputPrivateSubnetsIdsList := terraform.Output(t, terraformOptions, "private_subnets_ids_list") + outputManagementInstanceName := terraform.Output(t, terraformOptions, "management_name") + outputLBUrl := terraform.Output(t, terraformOptions, "load_balancer_url") + outputExternalLBId := terraform.Output(t, terraformOptions, "external_load_balancer_arn") + outputInternalLBId := terraform.Output(t, terraformOptions, "internal_load_balancer_arn") + outputExternalTGId := terraform.Output(t, terraformOptions, "external_lb_target_group_arn") + outputInternalTGId := terraform.Output(t, terraformOptions, "internal_lb_target_group_arn") + outputGwsASGId := terraform.Output(t, terraformOptions, "autoscale_autoscaling_group_arn") + outputSecurityGroup := terraform.Output(t, terraformOptions, "autoscale_security_group_id") + + asgName := terraform.Output(t, terraformOptions, "autoscale_autoscaling_group_name") + asgCapacityInfo := aws.GetCapacityInfoForAsg(t, asgName, region) + awsInstancesIds := aws.GetInstanceIdsForAsg(t, asgName, region) + + // website::tag::3:: + // Verify the ASG's Gateway instances contain the expected Name tag value + for _, instanceId := range awsInstancesIds { + // Look up the tags for the given Instance ID + instanceTags := aws.GetTagsForEc2Instance(t, region, instanceId) + + nameTag, containsNameTag := instanceTags["Name"] + assert.True(t, containsNameTag) + assert.Equal(t, qsAutoscaleGatewayExpectedName, nameTag) + } + + // Verify the ASG capacity info matches the expected + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMax), asgCapacityInfo.MaxCapacity) + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMin), asgCapacityInfo.MinCapacity) + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMin), asgCapacityInfo.CurrentCapacity) + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMin), asgCapacityInfo.DesiredCapacity) + + assert.NotEmpty(t, outputManagementInstanceName) + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputPublicSubnetsIdsList) + assert.NotEmpty(t, outputPrivateSubnetsIdsList) + assert.NotEmpty(t, outputLBUrl) + assert.NotEmpty(t, outputExternalLBId) + assert.NotEmpty(t, outputInternalLBId) + assert.NotEmpty(t, outputExternalTGId) + assert.NotEmpty(t, outputInternalTGId) + assert.NotEmpty(t, outputGwsASGId) + assert.NotEmpty(t, outputSecurityGroup) +} diff --git a/deprecated/terraform/aws/R80.40/tests/standalone_master_test.go b/deprecated/terraform/aws/R80.40/tests/standalone_master_test.go new file mode 100755 index 00000000..c04e7f78 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/standalone_master_test.go @@ -0,0 +1,112 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/aws" + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/standalone-master using terratest. +func TestStandaloneMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsStandaloneMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetStandaloneMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsStandaloneMaster(t, terraformOptions) +} + +func GetTerraformOptionsStandaloneMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../standalone-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMapSingle, + "private_subnets_map": privateSubnetsMapSingle, + "subnets_bit_length": subnetsBitLength, + + "standalone_name": standaloneExpectedName, + "standalone_instance_type": standaloneInstanceType, + "key_name": keyName, + "allocate_and_associate_eip": allocateAndAssociatePublicEip, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueGateway}, + + "standalone_version": standaloneVersion, + "admin_shell": adminShell, + "standalone_password_hash": passwordHash, + "standalone_maintenance_mode_password_hash": passwordHash, + + "resources_tag_name": resourcesTagName, + "standalone_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "standalone_bootstrap_script": standaloneBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + "admin_cidr": anywhereAddress, + "gateway_addresses": anywhereAddress, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetStandaloneMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsStandaloneMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsStandaloneMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputInternalRouteTableId := terraform.Output(t, terraformOptions, "internal_rtb_id") + outputVpcPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_public_subnets_ids_list") + outputVpcPrivateSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_private_subnets_ids_list") + outputStandaloneInstanceId := terraform.Output(t, terraformOptions, "standalone_instance_id") + outputStandaloneInstanceName := terraform.Output(t, terraformOptions, "standalone_instance_name") + outputStandalonePublicIP := terraform.Output(t, terraformOptions, "standalone_public_ip") + outputStandaloneSSH := terraform.Output(t, terraformOptions, "standalone_ssh") + outputStandaloneURL := terraform.Output(t, terraformOptions, "standalone_url") + + // website::tag::3:: + // Verify the Standalone's instances contain the expected Name tag value + instanceTags := aws.GetTagsForEc2Instance(t, region, outputStandaloneInstanceId) + nameTag, containsNameTag := instanceTags["Name"] + assert.True(t, containsNameTag) + assert.Equal(t, standaloneExpectedName, nameTag) + assert.Equal(t, standaloneExpectedName, outputStandaloneInstanceName) + + testTag, containsTestTag := instanceTags[expectedTestTagKey] + assert.True(t, containsTestTag) + assert.Equal(t, expectedTestTagValueGateway, testTag) + + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputInternalRouteTableId) + assert.NotEmpty(t, outputVpcPublicSubnetsIdsList) + assert.NotEmpty(t, outputVpcPrivateSubnetsIdsList) + assert.NotEmpty(t, outputStandaloneInstanceId) + assert.NotEmpty(t, outputStandaloneInstanceName) + assert.NotEmpty(t, outputStandalonePublicIP) + assert.NotEmpty(t, outputStandaloneSSH) + assert.NotEmpty(t, outputStandaloneURL) +} diff --git a/deprecated/terraform/aws/R80.40/tests/tgw_asg_master_test.go b/deprecated/terraform/aws/R80.40/tests/tgw_asg_master_test.go new file mode 100755 index 00000000..c5c98afa --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/tgw_asg_master_test.go @@ -0,0 +1,95 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/tgw-asg-master using terratest. +func TestTgwAsgMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsTgwAsgMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsTgwAsgMaster(t, terraformOptions) +} + +func GetTerraformOptionsTgwAsgMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../tgw-asg-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "allow_upload_download": allowUploadDownload, + + "gateway_name": crossAZClusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "gateways_min_group_size": autoscaleGroupExpectedCapacityMin, + "gateways_max_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "enable_cloudwatch": enableCloudWatch, + "asn": 6500, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "management_permissions": "Create with read-write permissions", + "management_predefined_role": predefinedRole, + "gateways_blades": gatewaysBlades, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + "gateway_management": gatewayManagement, + + "control_gateway_over_public_or_private_address": "private", + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsTgwAsgMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputVpcPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "public_subnets_ids_list") + outputManagementInstanceName := terraform.Output(t, terraformOptions, "management_instance_name") + outputConfigurationTemplate := terraform.Output(t, terraformOptions, "configuration_template") + outputControllerName := terraform.Output(t, terraformOptions, "controller_name") + outputManagementPublicIP := terraform.Output(t, terraformOptions, "management_public_ip") + outputManagementURL := terraform.Output(t, terraformOptions, "management_url") + outputAutoscalingGroupName := terraform.Output(t, terraformOptions, "autoscaling_group_name") + + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputVpcPublicSubnetsIdsList) + assert.NotEmpty(t, outputManagementInstanceName) + assert.NotEmpty(t, outputConfigurationTemplate) + assert.NotEmpty(t, outputControllerName) + assert.NotEmpty(t, outputManagementPublicIP) + assert.NotEmpty(t, outputManagementURL) + assert.NotEmpty(t, outputAutoscalingGroupName) +} diff --git a/deprecated/terraform/aws/R80.40/tests/tgw_cross_az_cluster_master_test.go b/deprecated/terraform/aws/R80.40/tests/tgw_cross_az_cluster_master_test.go new file mode 100755 index 00000000..8220bcd3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/tgw_cross_az_cluster_master_test.go @@ -0,0 +1,103 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" + "testing" +) + +// Test the Terraform module in aws/tgw-cross-az-cluster-master using terratest. +func TestTgwCrossAzClusterMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsTgwCrossAzClusterMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetTgwCrossAzClusterMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsTgwCrossAzClusterMaster(t, terraformOptions) +} + +func GetTerraformOptionsTgwCrossAzClusterMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../tgw-cross-az-cluster-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "private_subnets_map": privateSubnetsMap, + "tgw_subnets_map": tgwSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": crossAZClusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + + "predefined_role": predefinedRole, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "memberAToken": gatewaySmart1CloudToken, + "memberBToken": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetTgwCrossAzClusterMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsTgwCrossAzClusterMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsTgwCrossAzClusterMaster(t *testing.T, terraformOptions *terraform.Options) { + outputClusterPublicIP := terraform.Output(t, terraformOptions, "cluster_public_ip") + outputMemberAPublicIP := terraform.Output(t, terraformOptions, "member_a_public_ip") + outputMemberBPublicIP := terraform.Output(t, terraformOptions, "member_b_public_ip") + outputMemberASSH := terraform.Output(t, terraformOptions, "member_a_ssh") + outputMemberBSSH := terraform.Output(t, terraformOptions, "member_b_ssh") + outputMemberAURL := terraform.Output(t, terraformOptions, "member_a_url") + outputMemberBURL := terraform.Output(t, terraformOptions, "member_b_url") + outputMemberAENI := terraform.Output(t, terraformOptions, "member_a_eni") + outputMemberBENI := terraform.Output(t, terraformOptions, "member_b_eni") + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + + assert.NotEmpty(t, outputClusterPublicIP) + assert.NotEmpty(t, outputMemberAPublicIP) + assert.NotEmpty(t, outputMemberASSH) + assert.NotEmpty(t, outputMemberAURL) + assert.NotEmpty(t, outputMemberBPublicIP) + assert.NotEmpty(t, outputMemberBSSH) + assert.NotEmpty(t, outputMemberBURL) + assert.NotEmpty(t, outputMemberAENI) + assert.NotEmpty(t, outputMemberBENI) + assert.NotEmpty(t, outputVpcId) +} diff --git a/deprecated/terraform/aws/R80.40/tests/tgw_gwlb_master_test.go b/deprecated/terraform/aws/R80.40/tests/tgw_gwlb_master_test.go new file mode 100755 index 00000000..da863cea --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tests/tgw_gwlb_master_test.go @@ -0,0 +1,110 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/tgw-gwlb-master using terratest. +func TestTgwGwlbMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsTgwGwlbMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsTgwGwlbMaster(t, terraformOptions) +} + +func GetTerraformOptionsTgwGwlbMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../tgw-gwlb-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "tgw_subnets_map": tgwSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "availability_zones": availabilityZones, + "number_of_AZs": numberOfAZs, + + "nat_gw_subnet_1_cidr": "10.0.13.0/24", + "nat_gw_subnet_2_cidr": "10.0.23.0/24", + + "gwlbe_subnet_1_cidr": "10.0.14.0/24", + "gwlbe_subnet_2_cidr": "10.0.24.0/24", + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "volume_size": volumeSize, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "allow_upload_download": allowUploadDownload, + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + "admin_shell": adminShell, + + "gateway_load_balancer_name": gwlbExpectedName, + "target_group_name": targetGroup1Name, + "enable_cross_zone_load_balancing": enableCrossZoneLoadBalancing, + + "gateway_name": gatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "minimum_group_size": autoscaleGroupExpectedCapacityMin, + "maximum_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "gateways_provision_address_type": gatewaysProvisionAddressType, + "allocate_public_IP": allocatePublicIP, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "gateways_policy": gatewaysPolicy, + "gateway_management": gatewayManagement, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + + "volume_type": volumeType, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsTgwGwlbMaster(t *testing.T, terraformOptions *terraform.Options) { + outputDeployment := terraform.Output(t, terraformOptions, "Deployment") + outputManagementPublicIP := terraform.Output(t, terraformOptions, "management_public_ip") + outputGWLBARN := terraform.Output(t, terraformOptions, "gwlb_arn") + outputGWLBServiceName := terraform.Output(t, terraformOptions, "gwlb_service_name") + outputGWLBName := terraform.Output(t, terraformOptions, "gwlb_name") + outputGWLBControllerName := terraform.Output(t, terraformOptions, "controller_name") + outputConfigurationTemplateName := terraform.Output(t, terraformOptions, "template_name") + + assert.Equal(t, outputGWLBName, gwlbExpectedName) + assert.Equal(t, outputGWLBControllerName, gwlbControlllerExpectedName) + assert.Equal(t, outputConfigurationTemplateName, configurationTemplate) + + assert.NotEmpty(t, outputDeployment) + assert.NotEmpty(t, outputManagementPublicIP) + assert.NotEmpty(t, outputGWLBARN) + assert.NotEmpty(t, outputGWLBServiceName) +} diff --git a/deprecated/terraform/aws/R80.40/tgw-asg-master/README.md b/deprecated/terraform/aws/R80.40/tgw-asg-master/README.md new file mode 100755 index 00000000..4c9ec6f8 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg-master/README.md @@ -0,0 +1,223 @@ +# Check Point CloudGuard Network Transit Gateway Auto Scaling Group Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group for Transit Gateway with an optional Management Server in a new VPC. + +These types of Terraform resources are supported: +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Subnet](https://www.terraform.io/docs/providers/aws/r/subnet.html) +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [CloudGuard Network for AWS Transit Gateway R80.10 and Higher Deployment Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_AWS_Transit_Gateway/Content/Topics-AWS-TGW-R80-10-AG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/tgw-asg +- /terraform/aws/autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/tgw-asg-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/tgw-asg, /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/tgw-asg, /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/tgw-asg-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/tgw-asg-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + subnets_bit_length = 8 + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-gateway" + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = true + asn = "6500" + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + management_permissions = "Create with read-write permissions" + management_predefined_role = "" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + gateway_management = "Locally managed" + + // --- Automatic Provisioning with Security Management Server Settings --- + control_gateway_over_public_or_private_address = "private" + management_server = "management-server" + configuration_template = "template-name" + ``` + +- Conditional creation + - To create a Security Management server with IAM Role: + ``` + management_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + ``` + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Gateway | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| asn | The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways | string | n/a | 6500 | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R80.40-BYOL
- R80.40-PAYG
- R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| management_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read-write permissions | no | +| management_predefined_role | ((Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing' | string | n/a | "" | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | Allow gateways only from this network to communicate with the Security Management Server | string | valid CIDR | n/a | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| control_gateway_over_public_or_private_address | Determines if the gateways are provisioned using their private or public address | string | - private
- public | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | management-server | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | TGW-ASG-configuration | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| public_subnets_ids_list | A list of the public subnets ids | +| management_instance_name | The deployed Security Management AWS instance name | +| management_public_ip | The deployed Security Management Server AWS public ip | +| management_url | URL to the portal of the deployed Security Management Server | +| autoscaling_group_name | The name of the deployed AutoScaling Group | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | First release of Check Point Transit Gateway Auto Scaling Group Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/tgw-asg-master/locals.tf b/deprecated/terraform/aws/R80.40/tgw-asg-master/locals.tf new file mode 100755 index 00000000..467c4b4e --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg-master/locals.tf @@ -0,0 +1,66 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.management_permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.management_permissions) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_asn = "^[0-9]+$" + // Will fail if var.asn is invalid + regex_asn = regex(local.regex_valid_asn, var.asn) == var.asn ? 0 : "Variable [asn] must be a valid asn" + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^[0-9a-zA-Z-._]+$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^[0-9a-zA-Z-._]+$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-asg-master/main.tf b/deprecated/terraform/aws/R80.40/tgw-asg-master/main.tf new file mode 100755 index 00000000..a9fdd06e --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg-master/main.tf @@ -0,0 +1,55 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = {} + subnets_bit_length = var.subnets_bit_length +} + +module "launch_tgw_asg_into_vpc" { + source = "../tgw-asg" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + gateways_subnets = module.launch_vpc.public_subnets_ids_list + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + gateways_min_group_size = var.gateways_min_group_size + gateways_max_group_size = var.gateways_max_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + enable_cloudwatch = var.enable_cloudwatch + asn = var.asn + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + management_permissions = var.management_permissions + management_predefined_role = var.management_predefined_role + gateways_blades = var.gateways_blades + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + gateway_management = var.gateway_management + control_gateway_over_public_or_private_address = var.control_gateway_over_public_or_private_address + management_server = var.management_server + configuration_template = var.configuration_template +} diff --git a/deprecated/terraform/aws/R80.40/tgw-asg-master/output.tf b/deprecated/terraform/aws/R80.40/tgw-asg-master/output.tf new file mode 100755 index 00000000..ed183c0a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg-master/output.tf @@ -0,0 +1,24 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "management_instance_name" { + value = module.launch_tgw_asg_into_vpc.management_instance_name +} +output "configuration_template" { + value = module.launch_tgw_asg_into_vpc.configuration_template +} +output "controller_name" { + value = module.launch_tgw_asg_into_vpc.controller_name +} +output "management_public_ip" { + value = module.launch_tgw_asg_into_vpc.management_public_ip +} +output "management_url" { + value = module.launch_tgw_asg_into_vpc.management_url +} +output "autoscaling_group_name" { + value = module.launch_tgw_asg_into_vpc.autoscaling_group_name +} diff --git a/deprecated/terraform/aws/R80.40/tgw-asg-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/tgw-asg-master/terraform.tfvars new file mode 100755 index 00000000..7807cc3d --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg-master/terraform.tfvars @@ -0,0 +1,47 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +subnets_bit_length = 8 + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-gateway" +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true +asn = "6500" + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +management_permissions = "Create with read-write permissions" +management_predefined_role = "" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" +gateway_management = "Locally managed" + +// --- Automatic Provisioning with Security Management Server Settings --- +control_gateway_over_public_or_private_address = "private" +management_server = "management-server" +configuration_template = "template-name" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-asg-master/variables.tf b/deprecated/terraform/aws/R80.40/tgw-asg-master/variables.tf new file mode 100755 index 00000000..a709a74f --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg-master/variables.tf @@ -0,0 +1,217 @@ +// Module: Check Point CloudGuard Network Transit Gateway Auto Scaling Group +// Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server in a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" + default = true +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "asn" { + type = string + description = "The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways" + default = "6500" +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "management_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read-write permissions" +} +variable "management_predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'" + default = "" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "management-server" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "TGW-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} diff --git a/deprecated/terraform/aws/R80.40/tgw-asg-master/versions.tf b/deprecated/terraform/aws/R80.40/tgw-asg-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/tgw-asg/README.md b/deprecated/terraform/aws/R80.40/tgw-asg/README.md new file mode 100755 index 00000000..3861bec6 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg/README.md @@ -0,0 +1,213 @@ +# Check Point CloudGuard Network Transit Gateway Auto Scaling Group Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group for Transit Gateway with an optional Management Server into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [CloudGuard Network for AWS Transit Gateway R80.10 and Higher Deployment Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_AWS_Transit_Gateway/Content/Topics-AWS-TGW-R80-10-AG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/tgw-asg/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/tgw-asg/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/tgw-asg/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Network Configuration --- + vpc_id = "vpc-12345678" + gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-gateway" + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = true + asn = "6500" + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + management_permissions = "Create with read-write permissions" + management_predefined_role = "" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + gateway_management = "Locally managed" + + // --- Automatic Provisioning with Security Management Server Settings --- + control_gateway_over_public_or_private_address = "private" + management_server = "management-server" + configuration_template = "template-name" + ``` + +- Conditional creation + - To create a Security Management server with IAM Role: + ``` + management_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + ``` + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------|----------| +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | list(string) | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Gateway | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| asn | The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways | string | n/a | 6500 | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R80.40-BYOL
- R80.40-PAYG
- R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| management_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read-write permissions | no | +| management_predefined_role | ((Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing' | string | n/a | "" | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | Allow gateways only from this network to communicate with the Security Management Server | string | valid CIDR | n/a | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| control_gateway_over_public_or_private_address | Determines if the gateways are provisioned using their private or public address | string | - private
- public | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | management-server | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | TGW-ASG-configuration | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| management_instance_name | The deployed Security Management AWS instance name | +| management_public_ip | The deployed Security Management Server AWS public ip | +| management_url | URL to the portal of the deployed Security Management Server | +| autoscaling_group_name | The name of the deployed AutoScaling Group | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230626 | Fixed missing x-chkp-* tags on Auto Scale Group | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | First release of Check Point Transit Gateway Auto Scaling Group Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/tgw-asg/locals.tf b/deprecated/terraform/aws/R80.40/tgw-asg/locals.tf new file mode 100755 index 00000000..7ecd5cf4 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg/locals.tf @@ -0,0 +1,64 @@ +locals { + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.management_permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.management_permissions) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_asn = "^[0-9]+$" + // Will fail if var.asn is invalid + regex_asn = regex(local.regex_valid_asn, var.asn) == var.asn ? 0 : "Variable [asn] must be a valid asn" + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^[0-9a-zA-Z-._]+$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^[0-9a-zA-Z-._]+$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-asg/main.tf b/deprecated/terraform/aws/R80.40/tgw-asg/main.tf new file mode 100755 index 00000000..8b7b3cf1 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg/main.tf @@ -0,0 +1,64 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "autoscale" { + source = "../autoscale" + providers = { + aws = aws + } + + vpc_id = var.vpc_id + subnet_ids = var.gateways_subnets + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + metadata_imdsv2_required = var.metadata_imdsv2_required + minimum_group_size = var.gateways_min_group_size + maximum_group_size = var.gateways_max_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding tgw identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: autoscale_tgw' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"autoscale_tgw\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo 'Setting ASN to: ${var.asn}'; clish -c 'set as ${var.asn}' -s; echo -e '\nFinished Bootstrap script\n'" + gateways_provision_address_type = var.control_gateway_over_public_or_private_address + management_server = var.management_server + configuration_template = var.configuration_template +} + +data "aws_region" "current"{} + +module "management" { + providers = { + aws = aws + } + count = local.deploy_management_condition ? 1 : 0 + source = "../management" + + vpc_id = var.vpc_id + subnet_id = var.gateways_subnets[0] + management_name = var.management_server + management_instance_type = var.management_instance_type + key_name = var.key_name + allocate_and_associate_eip = true + volume_encryption = var.enable_volume_encryption ? "alias/aws/ebs" : "" + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + iam_permissions = var.management_permissions + predefined_role = var.management_predefined_role + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + allow_upload_download = var.allow_upload_download + admin_cidr = var.admin_cidr + gateway_addresses = var.gateways_addresses + gateway_management = var.gateway_management + management_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding tgw identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: management_tgw_asg' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"management_tgw_asg\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo 'Configuring VPN community: tgw-community'; [[ -d /opt/CPcme/menu/additions ]] && /opt/CPcme/menu/additions/config-community.sh \"tgw-community\" || /etc/fw/scripts/autoprovision/config-community.sh \"tgw-community\"; echo 'Setting VPN rules'; mgmt_cli -r true add access-layer name 'Inline'; mgmt_cli -r true add access-rule layer Network position 1 name 'tgw-community VPN Traffic Rule' vpn.directional.1.from 'tgw-community' vpn.directional.1.to 'tgw-community' vpn.directional.2.from 'tgw-community' vpn.directional.2.to External_clear action 'Apply Layer' inline-layer 'Inline'; mgmt_cli -r true add nat-rule package standard position bottom install-on 'Policy Targets' original-source All_Internet translated-source All_Internet method hide; echo 'Creating CME configuration'; autoprov_cfg -f init AWS -mn ${var.management_server} -tn ${var.configuration_template} -cn tgw-controller -po Standard -otp ${var.gateway_SICKey} -r ${data.aws_region.current.name} -ver ${split("-", var.gateway_version)[0]} -iam -dt TGW; autoprov_cfg -f set controller AWS -cn tgw-controller -sv -com tgw-community; autoprov_cfg -f set template -tn ${var.configuration_template} -vpn -vd '''' -con tgw-community; ${var.gateways_blades} && autoprov_cfg -f set template -tn ${var.configuration_template} -ia -ips -appi -av -ab; echo -e '\nFinished Bootstrap script\n'" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-asg/output.tf b/deprecated/terraform/aws/R80.40/tgw-asg/output.tf new file mode 100755 index 00000000..8a282a53 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg/output.tf @@ -0,0 +1,18 @@ +output "management_instance_name" { + value = module.management[0].management_instance_name +} +output "configuration_template" { + value = var.configuration_template +} +output "controller_name" { + value = "tgw-controller" +} +output "management_public_ip" { + value = module.management[0].management_public_ip +} +output "management_url" { + value = module.management[0].management_url +} +output "autoscaling_group_name" { + value = module.autoscale.autoscale_autoscaling_group_name +} diff --git a/deprecated/terraform/aws/R80.40/tgw-asg/terraform.tfvars b/deprecated/terraform/aws/R80.40/tgw-asg/terraform.tfvars new file mode 100755 index 00000000..943f16b4 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Network Configuration --- +vpc_id = "vpc-12345678" +gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-gateway" +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true +asn = "65000" + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +management_permissions = "Create with read-write permissions" +management_predefined_role = "" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" +gateway_management = "Locally managed" + +// --- Automatic Provisioning with Security Management Server Settings --- +control_gateway_over_public_or_private_address = "private" +management_server = "management-server" +configuration_template = "template-name" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-asg/variables.tf b/deprecated/terraform/aws/R80.40/tgw-asg/variables.tf new file mode 100755 index 00000000..9a9a47e1 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg/variables.tf @@ -0,0 +1,211 @@ +// Module: Check Point CloudGuard Network Transit Gateway Auto Scaling Group +// Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "vpc_id" { + type = string +} +variable "gateways_subnets" { + type = list(string) + description = "Select at least 2 external subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" + default = true +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "asn" { + type = string + description = "The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways" + default = "6500" +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "management_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read-write permissions" +} +variable "management_predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'" + default = "" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "management-server" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "TGW-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} diff --git a/deprecated/terraform/aws/R80.40/tgw-asg/versions.tf b/deprecated/terraform/aws/R80.40/tgw-asg/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-asg/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/README.md b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/README.md new file mode 100755 index 00000000..1dbcaeef --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/README.md @@ -0,0 +1,208 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster for Transit Gateway Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster with a new VPC on AWS for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + + - Variables are configured in /terraform/aws/cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 + } + tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1 \"us-east-1b\" = 2} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3 \"us-east-1b\" = 4} ) | map | n/a | n/a | yes | +| tgw_subnets_map | A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------|-----------------------------------| +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221123 | R81.20 version support | +| 20221229 | Removed unsupported versions | +| 20221123 | First release of Check Point Security Cluster Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/locals.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/locals.tf new file mode 100755 index 00000000..387fb7c1 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/locals.tf @@ -0,0 +1,61 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/main.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/main.tf new file mode 100755 index 00000000..d04b9548 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/main.tf @@ -0,0 +1,73 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + tgw_subnets_map = var.tgw_subnets_map + subnets_bit_length = var.subnets_bit_length +} +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnet1" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} +resource "aws_route_table_association" "private_rtb_to_private_subnet2" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[1] +} +module "tgw_cluster_into_vpc" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + source = "../tgw-cross-az-cluster" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_1 = module.launch_vpc.public_subnets_ids_list[0] + public_subnet_2 = module.launch_vpc.public_subnets_ids_list[1] + private_subnet_1 = module.launch_vpc.private_subnets_ids_list[0] + private_subnet_2 = module.launch_vpc.private_subnets_ids_list[1] + tgw_subnet_1_id = module.launch_vpc.tgw_subnets_ids_list[0] + tgw_subnet_2_id =module.launch_vpc.tgw_subnets_ids_list[1] + private_route_table = aws_route_table.private_subnet_rtb.id + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + memberAToken = var.memberAToken + memberBToken = var.memberBToken + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + volume_type = var.volume_type +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/output.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/output.tf new file mode 100755 index 00000000..fd143a67 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/output.tf @@ -0,0 +1,30 @@ +output "cluster_public_ip" { + value = module.tgw_cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.tgw_cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.tgw_cluster_into_vpc.member_b_public_ip +} +output "member_a_ssh" { + value = module.tgw_cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.tgw_cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.tgw_cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.tgw_cluster_into_vpc.member_b_url +} +output "member_a_eni" { + value = module.tgw_cluster_into_vpc.member_a_eni +} +output "member_b_eni" { + value = module.tgw_cluster_into_vpc.member_b_eni +} +output "vpc_id" { + value = module.launch_vpc.vpc_id +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/terraform.tfvars new file mode 100755 index 00000000..2a1fee10 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/terraform.tfvars @@ -0,0 +1,48 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.29.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 +} +tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true + +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/variables.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/variables.tf new file mode 100755 index 00000000..1485389b --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/variables.tf @@ -0,0 +1,200 @@ +// Module: Check Point CloudGuard Network Security Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// ---VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +resource "null_resource" "tgw_availability_zones_validation1" { + count = length(var.public_subnets_map) == 2 ? 0 : "variable public_subnets_map size must be equal to variable 2" +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " +} +resource "null_resource" "tgw_availability_zones_validation2" { + count = length(var.private_subnets_map) == 2 ? 0 : "variable private_subnets_map size must be equal to variable 2" +} +variable "tgw_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3} ) " +} +resource "null_resource" "tgw_availability_zones_validation3" { + count = length(var.tgw_subnets_map) == 2 ? 0 : "variable tgw_subnets_map size must be equal to variable 2" +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/versions.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/README.md b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/README.md new file mode 100755 index 00000000..ac9a5fc2 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/README.md @@ -0,0 +1,204 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster for Transit Gateway Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster into an existing VPC on AWS for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-1234" + public_subnet_1 = "subnet-1234" + public_subnet_2 = "subnet-2345" + private_subnet_1 = "subnet-3456" + private_subnet_2 = "subnet-4567" + tgw_subnet_1_id = "subnet-5678" + tgw_subnet_2_id = "subnet-6789" + private_route_table = "" + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the cluster. The cluster's public IPs will be generated from this subnet | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the cluster. The cluster's private IPs will be generated from this subnet | string | n/a | n/a | yes | +| tgw_subnet_1_id | The TGW attachment subnet ID located in the 1st Availability Zone | string | n/a | n/a | yes | +| tgw_subnet_2_id | The TGW attachment subnet ID located in the 2st Availability Zone | string | n/a | n/a | yes | +| private_route_table | (Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------|-----------------------------------| +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221229 | Removed unsupported versions | +| 20221123 | R81.20 version support | +| 20221123 | First release of Check Point Security Cluster Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/locals.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/locals.tf new file mode 100755 index 00000000..9a9929b7 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/locals.tf @@ -0,0 +1,60 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + provided_roue_table = var.private_route_table == "" ? 0 : 1 + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/main.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/main.tf new file mode 100755 index 00000000..4ae319ab --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/main.tf @@ -0,0 +1,62 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + + +module "cluster_into_vpc" { + source = "../cross-az-cluster" + providers = { + aws = aws + } + + vpc_id = var.vpc_id + public_subnet_ids = tolist([var.public_subnet_1, var.public_subnet_2]) + private_subnet_ids = tolist([var.private_subnet_1, var.private_subnet_2]) + private_route_table = var.private_route_table + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + memberAToken = var.memberAToken + memberBToken = var.memberBToken + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + volume_type = var.volume_type +} +resource "aws_route_table" "tgw_route_table" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + network_interface_id = module.cluster_into_vpc.member_a_eni + } + tags = { + Name = "TGW Attachment Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment1_rtb_assoc" { + subnet_id = var.tgw_subnet_1_id + route_table_id = aws_route_table.tgw_route_table.id +} +resource "aws_route_table_association" "tgw_attachment2_rtb_assoc" { + subnet_id = var.tgw_subnet_2_id + route_table_id = aws_route_table.tgw_route_table.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/output.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/output.tf new file mode 100755 index 00000000..2aa6d333 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/output.tf @@ -0,0 +1,27 @@ +output "cluster_public_ip" { + value = module.cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.cluster_into_vpc.member_b_public_ip +} +output "member_a_eni" { + value = module.cluster_into_vpc.member_a_eni +} +output "member_a_ssh" { + value = module.cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.cluster_into_vpc.member_b_url +} +output "member_b_eni" { + value = module.cluster_into_vpc.member_b_eni +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/terraform.tfvars b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/terraform.tfvars new file mode 100755 index 00000000..c1008d0d --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-1234" +public_subnet_1 = "subnet-1234" +public_subnet_2 = "subnet-2345" +private_subnet_1 = "subnet-3456" +private_subnet_2 = "subnet-4567" +tgw_subnet_1_id = "subnet-5678" +tgw_subnet_2_id = "subnet-6789" +private_route_table = "" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true + +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/variables.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/variables.tf new file mode 100755 index 00000000..eb330795 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/variables.tf @@ -0,0 +1,201 @@ +// Module: Check Point CloudGuard Network Security Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_1" { + type = string + description = "The public subnet ID of the cluster that located in the 1st Availability Zone" +} +variable "public_subnet_2" { + type = string + description = "The public subnet of the cluster that located in the 2st Availability Zone" +} +variable "private_subnet_1" { + type = string + description = "The private subnet of the cluster that located in the 1st Availability Zone" +} +variable "private_subnet_2" { + type = string + description = "The private subnet of the cluster that located in the 2st Availability Zone" +} +variable "tgw_subnet_1_id" { + type = string + description = "The TGW attachment subnet ID located in the 1st Availability Zone" +} +variable "tgw_subnet_2_id" { + type = string + description = "The TGW attachment subnet ID located in the 2st Availability Zone" +} +variable "private_route_table" { + type = string + description = "(Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/versions.tf b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-cross-az-cluster/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb-master/README.md b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/README.md new file mode 100755 index 00000000..e03fc496 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/README.md @@ -0,0 +1,264 @@ +# Check Point CloudGuard Network Gateway Load Balancer for Transit Gateway Terraform Master module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into new Centralized Security VPC for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/modules/vpc +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +- /terraform/aws/gwlb + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` + - Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + "us-east-1c" = 3 + "us-east-1d" = 4 + } + tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 + "us-east-1c" = 7 + "us-east-1d" = 8 + } + subnets_bit_length = 8 + + availability_zones = ["us-east-1a", "us-east-1b", "us-east-1c", "us-east-1d"] + number_of_AZs = 4 + + nat_gw_subnet_1_cidr ="10.0.13.0/24" + nat_gw_subnet_2_cidr = "10.0.23.0/24" + nat_gw_subnet_3_cidr = "10.0.33.0/24" + nat_gw_subnet_4_cidr = "10.0.43.0/24" + + gwlbe_subnet_1_cidr = "10.0.14.0/24" + gwlbe_subnet_2_cidr = "10.0.24.0/24" + gwlbe_subnet_3_cidr = "10.0.34.0/24" + gwlbe_subnet_4_cidr = "10.0.44.0/24" + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb" + target_group_name = "tg1" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + + // --- Other parameters --- + volume_type = "gp3" + ``` + +- Conditional creation + - To enable cloudwatch for tgw-gwlb-master: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| availability_zones | The Availability Zones (AZs) to use for the subnets in the VPC. | string | n/a | n/a | yes | +| Number_of_AZs | Number of Availability Zones to use in the VPC. | number | n/a | 2 | yes | +| tgw_subnets_map | A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| nat_gw_subnet_1_cidr | CIDR block for NAT subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.13.0/24 | yes | +| nat_gw_subnet_2_cidr | CIDR block for NAT subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.23.0/24 | yes | +| nat_gw_subnet_3_cidr | CIDR block for NAT subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.33.0/24 | yes | +| nat_gw_subnet_4_cidr | CIDR block for NAT subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.43.0/24 | yes | +| gwlbe_subnet_1_cidr | CIDR block for GWLBe subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.14.0/24 | yes | +| gwlbe_subnet_2_cidr | CIDR block for GWLBe subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.24.0/24 | yes | +| gwlbe_subnet_3_cidr | CIDR block for GWLBe subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.34.0/24 | yes | +| gwlbe_subnet_4_cidr | CIDR block for GWLBe subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.44.0/24 | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-ter | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb-terraform | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1-terraform | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | gwlb-terraform | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R80.40-BYOL
- R80.40-PAYG
- R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|----------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point CloudGuar d Network Gateway Load Balancer for Transit Gateway Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb-master/locals.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/locals.tf new file mode 100755 index 00000000..d75eeaa5 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/locals.tf @@ -0,0 +1,62 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.volume_type] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) + + + #note: we need to add validiation for every subnet in masters solution +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb-master/main.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/main.tf new file mode 100755 index 00000000..3b616ebc --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/main.tf @@ -0,0 +1,85 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = {} + tgw_subnets_map = var.tgw_subnets_map + subnets_bit_length = var.subnets_bit_length +} +module "tgw-gwlb"{ + source = "../tgw-gwlb" + providers = { + aws = aws + } + vpc_id = module.launch_vpc.vpc_id + gateways_subnets = module.launch_vpc.public_subnets_ids_list + number_of_AZs = var.number_of_AZs + availability_zones = var.availability_zones + internet_gateway_id = module.launch_vpc.aws_igw + + transit_gateway_attachment_subnet_1_id = element(module.launch_vpc.tgw_subnets_ids_list, 0) + transit_gateway_attachment_subnet_2_id = element(module.launch_vpc.tgw_subnets_ids_list, 1) + transit_gateway_attachment_subnet_3_id = var.number_of_AZs >= 3 ? element(module.launch_vpc.tgw_subnets_ids_list, 2) : "" + transit_gateway_attachment_subnet_4_id = var.number_of_AZs >= 4 ? element(module.launch_vpc.tgw_subnets_ids_list, 3) : "" + + nat_gw_subnet_1_cidr = var.nat_gw_subnet_1_cidr + nat_gw_subnet_2_cidr = var.nat_gw_subnet_2_cidr + nat_gw_subnet_3_cidr = var.nat_gw_subnet_3_cidr + nat_gw_subnet_4_cidr = var.nat_gw_subnet_4_cidr + + gwlbe_subnet_1_cidr = var.gwlbe_subnet_1_cidr + gwlbe_subnet_2_cidr = var.gwlbe_subnet_2_cidr + gwlbe_subnet_3_cidr = var.gwlbe_subnet_3_cidr + gwlbe_subnet_4_cidr = var.gwlbe_subnet_4_cidr + + // --- General Settings --- + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + volume_size = var.volume_size + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + management_server = var.management_server + configuration_template = var.configuration_template + admin_shell = var.admin_shell + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = var.gateway_load_balancer_name + target_group_name = var.target_group_name + enable_cross_zone_load_balancing = var.enable_cross_zone_load_balancing + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateway_management = var.gateway_management + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + + volume_type = var.volume_type +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb-master/output.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/output.tf new file mode 100755 index 00000000..67085776 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/output.tf @@ -0,0 +1,24 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "management_public_ip" { + depends_on = [module.tgw-gwlb] + value = module.tgw-gwlb[*].management_public_ip +} +output "gwlb_arn" { + depends_on = [module.tgw-gwlb] + value = module.tgw-gwlb[*].gwlb_arn +} +output "gwlb_service_name" { + depends_on = [module.tgw-gwlb] + value = module.tgw-gwlb[*].gwlb_service_name +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb-master/terraform.tfvars b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/terraform.tfvars new file mode 100755 index 00000000..bdb7a361 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/terraform.tfvars @@ -0,0 +1,76 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + "us-east-1c" = 3 + "us-east-1d" = 4 +} +tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 + "us-east-1c" = 7 + "us-east-1d" = 8 +} +subnets_bit_length = 8 + +availability_zones = ["us-east-1a", "us-east-1b", "us-east-1c", "us-east-1d"] +number_of_AZs = 4 + +nat_gw_subnet_1_cidr = "10.0.13.0/24" +nat_gw_subnet_2_cidr = "10.0.23.0/24" +nat_gw_subnet_3_cidr = "10.0.33.0/24" +nat_gw_subnet_4_cidr = "10.0.43.0/24" + +gwlbe_subnet_1_cidr = "10.0.14.0/24" +gwlbe_subnet_2_cidr = "10.0.24.0/24" +gwlbe_subnet_3_cidr = "10.0.34.0/24" +gwlbe_subnet_4_cidr = "10.0.44.0/24" + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb-master/variables.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/variables.tf new file mode 100755 index 00000000..af425811 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/variables.tf @@ -0,0 +1,326 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// ---VPC Network Configuration --- +variable "number_of_AZs" { + type = number + description = "Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter" + default = 2 +} +variable "availability_zones"{ + type = list(string) + description = "The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved)" +} +resource "null_resource" "tgw_availability_zones_validation1" { + count = var.number_of_AZs == length(var.availability_zones) ? 0 : "variable availability_zones list size must be equal to variable num_of_AZs" +} +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +resource "null_resource" "tgw_availability_zones_validation2" { + count = var.number_of_AZs == length(var.public_subnets_map) ? 0 : "variable public_subnets_map size must be equal to variable num_of_AZs" +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} +variable "tgw_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +resource "null_resource" "tgw_availability_zones_validation3" { + count = var.number_of_AZs == length(var.tgw_subnets_map) ? 0 : "variable tgw_subnets_map size must be equal to variable num_of_AZs" +} +variable "nat_gw_subnet_1_cidr" { + type = string + description = "CIDR block for NAT subnet 1 located in the 1st Availability Zone" + default = "10.0.13.0/24" +} +variable "nat_gw_subnet_2_cidr" { + type = string + description = "CIDR block for NAT subnet 2 located in the 2st Availability Zone" + default = "10.0.23.0/24" +} +variable "nat_gw_subnet_3_cidr" { + type = string + description = "CIDR block for NAT subnet 3 located in the 3st Availability Zone" + default = "10.0.33.0/24" +} +variable "nat_gw_subnet_4_cidr" { + type = string + description = "CIDR block for NAT subnet 4 located in the 4st Availability Zone" + default = "10.0.43.0/24" +} +variable "gwlbe_subnet_1_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 1 located in the 1st Availability Zone" + default = "10.0.14.0/24" +} +variable "gwlbe_subnet_2_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 2 located in the 2st Availability Zone" + default = "10.0.24.0/24" +} +variable "gwlbe_subnet_3_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 3 located in the 3st Availability Zone" + default = "10.0.34.0/24" +} +variable "gwlbe_subnet_4_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 4 located in the 4st Availability Zone" + default = "10.0.44.0/24" +} +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." + default = "gwlb-management-server" +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + default = "gwlb-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb-master/versions.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb/README.md b/deprecated/terraform/aws/R80.40/tgw-gwlb/README.md new file mode 100755 index 00000000..e94a1eea --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb/README.md @@ -0,0 +1,263 @@ +# Check Point CloudGuard Network Gateway Load Balancer for Transit Gateway Terraform module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into existing Centralized Security VPC for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [VPC](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/vpc) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +- /terraform/aws/gwlb +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` + - Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + internet_gateway_id ="igw-12345" + availability_zones = ["us-east-1a", "us-east-1b"] + number_of_AZs = 2 + gateways_subnets= ["subnet-123456", "subnet-234567"] + + transit_gateway_attachment_subnet_1_id="subnet-3456" + transit_gateway_attachment_subnet_2_id="subnet-4567" + transit_gateway_attachment_subnet_3_id="subnet-5678" + transit_gateway_attachment_subnet_4_id="subnet-6789" + + nat_gw_subnet_1_cidr ="10.0.13.0/24" + nat_gw_subnet_2_cidr = "10.0.23.0/24" + nat_gw_subnet_3_cidr = "10.0.33.0/24" + nat_gw_subnet_4_cidr = "10.0.43.0/24" + + gwlbe_subnet_1_cidr = "10.0.14.0/24" + gwlbe_subnet_2_cidr = "10.0.24.0/24" + gwlbe_subnet_3_cidr = "10.0.34.0/24" + gwlbe_subnet_4_cidr = "10.0.44.0/24" + + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb1" + target_group_name = "tg1" + connection_acceptance_required = "false" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "" + gateways_addresses = "" + + // --- Other parameters --- + VolumeType = "gp3" + + + ``` + +- Conditional creation + - To enable cloudwatch for tgw-gwlb: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| internet_gateway_id | VPC's Internet Gateway Id | string | n/a | n/a | yes | +| availability_zones | The Availability Zones (AZs) to use for the subnets in the VPC. | string | n/a | n/a | yes | +| Number_of_AZs | Number of Availability Zones to use in the VPC. | number | n/a | 2 | yes | +| Gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_1_id | The TGW attachment subnet ID located in the 1st Availability Zone | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_2_id | The TGW attachment subnet ID located in the 2st Availability Zone | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_3_id | The TGW attachment subnet ID located in the 3st Availability Zone | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_4_id | The TGW attachment subnet ID located in the 4st Availability Zone | string | n/a | n/a | yes | +| nat_gw_subnet_1_cidr | CIDR block for NAT subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.13.0/24 | yes | +| nat_gw_subnet_2_cidr | CIDR block for NAT subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.23.0/24 | yes | +| nat_gw_subnet_3_cidr | CIDR block for NAT subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.33.0/24 | yes | +| nat_gw_subnet_4_cidr | CIDR block for NAT subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.43.0/24 | yes | +| gwlbe_subnet_1_cidr | CIDR block for GWLBe subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.14.0/24 | yes | +| gwlbe_subnet_2_cidr | CIDR block for GWLBe subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.24.0/24 | yes | +| gwlbe_subnet_3_cidr | CIDR block for GWLBe subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.34.0/24 | yes | +| gwlbe_subnet_4_cidr | CIDR block for GWLBe subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.44.0/24 | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-ter | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb-terraform | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1-terraform | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | gwlb-terraform | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R80.40-BYOL
- R80.40-PAYG-NGTP
- R80.40-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R80.40-BYOL
- R80.40-PAYG
- R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point CloudGuard Network Gateway Load Balancer for Transit Gateway Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb/locals.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb/locals.tf new file mode 100755 index 00000000..0693df6d --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb/locals.tf @@ -0,0 +1,60 @@ +locals { + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) + + + #note: we need to add validiation for every subnet in masters solution +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb/main.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb/main.tf new file mode 100755 index 00000000..64ce7101 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb/main.tf @@ -0,0 +1,438 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + + +resource "aws_subnet" "gwlbe_subnet1" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 0) + cidr_block = var.gwlbe_subnet_1_cidr + tags = { + Name = "GWLBe subnet 1" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet1_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway1.id + } + tags = { + Name = "GWLBe Subnet 1 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet1_rtb_assoc" { + subnet_id = aws_subnet.gwlbe_subnet1.id + route_table_id = aws_route_table.gwlbe_subnet1_rtb.id +} + + +resource "aws_subnet" "gwlbe_subnet2" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 1) + cidr_block = var.gwlbe_subnet_2_cidr + tags = { + Name = "GWLBe subnet 2" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet2_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway2.id + } + tags = { + Name = "GWLBe Subnet 2 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet2_rtb_assoc" { + subnet_id = aws_subnet.gwlbe_subnet2.id + route_table_id = aws_route_table.gwlbe_subnet2_rtb.id +} + + +resource "aws_subnet" "gwlbe_subnet3" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 2) + cidr_block = var.gwlbe_subnet_3_cidr + tags = { + Name = "GWLBe subnet 3" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet3_rtb" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway3[0].id + } + tags = { + Name = "GWLBe Subnet 3 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet3_rtb_assoc" { + count = var.number_of_AZs >= 3 ? 1 :0 + subnet_id = aws_subnet.gwlbe_subnet3[0].id + route_table_id = aws_route_table.gwlbe_subnet3_rtb[0].id +} + + +resource "aws_subnet" "gwlbe_subnet4" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 3) + cidr_block = var.gwlbe_subnet_4_cidr + tags = { + Name = "GWLBe subnet 4" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet4_rtb" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway4[0].id + } + tags = { + Name = "GWLBe Subnet 4 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet4_rtb_assoc" { + count = var.number_of_AZs >= 4 ? 1 :0 + subnet_id = aws_subnet.gwlbe_subnet4[0].id + route_table_id = aws_route_table.gwlbe_subnet4_rtb[0].id +} + + + + +resource "aws_subnet" "nat_gw_subnet1" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 0) + cidr_block = var.nat_gw_subnet_1_cidr + tags = { + Name = "NAT subnet 1" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet1_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 1 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet1_rtb_assoc" { + subnet_id = aws_subnet.nat_gw_subnet1.id + route_table_id = aws_route_table.nat_gw_subnet1_rtb.id +} + +resource "aws_subnet" "nat_gw_subnet2" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 1) + cidr_block = var.nat_gw_subnet_2_cidr + tags = { + Name = "NAT subnet 2" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet2_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 2 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet2_rtb_assoc" { + subnet_id = aws_subnet.nat_gw_subnet2.id + route_table_id = aws_route_table.nat_gw_subnet2_rtb.id +} + +resource "aws_subnet" "nat_gw_subnet3" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 2) + cidr_block = var.nat_gw_subnet_3_cidr + tags = { + Name = "NAT subnet 3" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet3_rtb" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 3 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet3_rtb_assoc" { + count = var.number_of_AZs >= 3 ? 1 :0 + subnet_id = aws_subnet.nat_gw_subnet3[0].id + route_table_id = aws_route_table.nat_gw_subnet3_rtb[0].id +} + +resource "aws_subnet" "nat_gw_subnet4" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 3) + cidr_block = var.nat_gw_subnet_4_cidr + tags = { + Name = "NAT subnet 4" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet4_rtb" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 4 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet4_rtb_assoc" { + count = var.number_of_AZs >= 4 ? 1 :0 + subnet_id = aws_subnet.nat_gw_subnet4[0].id + route_table_id = aws_route_table.nat_gw_subnet4_rtb[0].id +} + +module "gwlb" { + source = "../gwlb" + providers = { + aws = aws + } + vpc_id = var.vpc_id + subnet_ids = var.gateways_subnets + + // --- General Settings --- + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + volume_size = var.volume_size + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + management_server = var.management_server + configuration_template = var.configuration_template + admin_shell = var.admin_shell + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = var.gateway_load_balancer_name + target_group_name = var.target_group_name + connection_acceptance_required = false + enable_cross_zone_load_balancing = var.enable_cross_zone_load_balancing + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateway_management = var.gateway_management + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + + volume_type = var.volume_type +} + +resource "aws_vpc_endpoint" "gwlb_endpoint1" { + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet1] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet1[*].id + tags = { + "Name" = "gwlb_endpoint1" + } +} +resource "aws_vpc_endpoint" "gwlb_endpoint2" { + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet2] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet2[*].id + tags = { + "Name" = "gwlb_endpoint2" + } +} +resource "aws_vpc_endpoint" "gwlb_endpoint3" { + count = var.number_of_AZs >= 3 ? 1 :0 + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet3] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet3[*].id + tags = { + "Name" = "gwlb_endpoint3" + } +} +resource "aws_vpc_endpoint" "gwlb_endpoint4" { + count = var.number_of_AZs >= 4 ? 1 :0 + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet4] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet4[*].id + tags = { + "Name" = "gwlb_endpoint4" + } +} + + +resource "aws_route_table" "tgw_attachment_subnet1_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint1.id + } + tags = { + Name = "TGW Attachment Subnet 1 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment1_rtb_assoc" { + subnet_id = var.transit_gateway_attachment_subnet_1_id + route_table_id = aws_route_table.tgw_attachment_subnet1_rtb.id +} +resource "aws_route_table" "tgw_attachment_subnet2_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint2.id + } + tags = { + Name = "TGW Attachment Subnet 2 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment2_rtb_assoc" { + subnet_id = var.transit_gateway_attachment_subnet_2_id + route_table_id = aws_route_table.tgw_attachment_subnet2_rtb.id +} +resource "aws_route_table" "tgw_attachment_subnet3_rtb" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint3[0].id + } + tags = { + Name = "TGW Attachment Subnet 3 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment3_rtb_assoc" { + count = var.number_of_AZs >= 3 ? 1 :0 + subnet_id = var.transit_gateway_attachment_subnet_3_id + route_table_id = aws_route_table.tgw_attachment_subnet3_rtb[0].id +} +resource "aws_route_table" "tgw_attachment_subnet4_rtb" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint4[0].id + } + tags = { + Name = "TGW Attachment Subnet 4 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment4_rtb_assoc" { + count = var.number_of_AZs >= 4 ? 1 :0 + subnet_id = var.transit_gateway_attachment_subnet_4_id + route_table_id = aws_route_table.tgw_attachment_subnet4_rtb[0].id +} + + +resource "aws_eip" "nat_gw_public_address1" { +} +resource "aws_eip" "nat_gw_public_address2" { +} +resource "aws_eip" "nat_gw_public_address3" { + count = var.number_of_AZs >= 3 ? 1 : 0 +} +resource "aws_eip" "nat_gw_public_address4" { + count = var.number_of_AZs >= 4 ? 1 : 0 +} + +resource "aws_nat_gateway" "nat_gateway1" { + depends_on = [aws_subnet.nat_gw_subnet1, aws_eip.nat_gw_public_address1] + allocation_id = aws_eip.nat_gw_public_address1.id + subnet_id = aws_subnet.nat_gw_subnet1.id + + tags = { + Name = "NatGW1" + } +} +resource "aws_nat_gateway" "nat_gateway2" { + depends_on = [aws_subnet.nat_gw_subnet2, aws_eip.nat_gw_public_address2] + allocation_id = aws_eip.nat_gw_public_address2.id + subnet_id = aws_subnet.nat_gw_subnet2.id + + tags = { + Name = "NatGW2" + } +} +resource "aws_nat_gateway" "nat_gateway3" { + count = var.number_of_AZs >= 3 ? 1 :0 + depends_on = [aws_subnet.nat_gw_subnet3, aws_eip.nat_gw_public_address3] + allocation_id = aws_eip.nat_gw_public_address3[0].id + subnet_id = aws_subnet.nat_gw_subnet3[0].id + + tags = { + Name = "NatGW3" + } +} +resource "aws_nat_gateway" "nat_gateway4" { + count = var.number_of_AZs >= 4 ? 1 :0 + depends_on = [aws_subnet.nat_gw_subnet4, aws_eip.nat_gw_public_address4] + allocation_id = aws_eip.nat_gw_public_address4[0].id + subnet_id = aws_subnet.nat_gw_subnet4[0].id + + tags = { + Name = "NatGW4" + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb/output.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb/output.tf new file mode 100755 index 00000000..15cb48a3 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb/output.tf @@ -0,0 +1,24 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "management_public_ip" { + depends_on = [module.gwlb] + value = module.gwlb[*].management_public_ip +} +output "gwlb_arn" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_arn +} +output "gwlb_service_name" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_service_name +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb/terraform.tfvars b/deprecated/terraform/aws/R80.40/tgw-gwlb/terraform.tfvars new file mode 100755 index 00000000..266b4d1a --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb/terraform.tfvars @@ -0,0 +1,69 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +internet_gateway_id ="igw-12345" +availability_zones = ["us-east-1a", "us-east-1b"] +number_of_AZs = 2 +gateways_subnets= ["subnet-123456", "subnet-234567"] + +transit_gateway_attachment_subnet_1_id="subnet-3456" +transit_gateway_attachment_subnet_2_id="subnet-4567" +transit_gateway_attachment_subnet_3_id="subnet-5678" +transit_gateway_attachment_subnet_4_id="subnet-6789" + +nat_gw_subnet_1_cidr ="10.0.13.0/24" +nat_gw_subnet_2_cidr = "10.0.23.0/24" +nat_gw_subnet_3_cidr = "10.0.33.0/24" +nat_gw_subnet_4_cidr = "10.0.43.0/24" + +gwlbe_subnet_1_cidr = "10.0.14.0/24" +gwlbe_subnet_2_cidr = "10.0.24.0/24" +gwlbe_subnet_3_cidr = "10.0.34.0/24" +gwlbe_subnet_4_cidr = "10.0.44.0/24" + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb/variables.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb/variables.tf new file mode 100755 index 00000000..52b97b13 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb/variables.tf @@ -0,0 +1,333 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// ---VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "internet_gateway_id" { + type = string + description = "VPC's Internet Gateway Id (e.g. igw-123a4567)" +} +variable "availability_zones"{ + type = list(string) + description = "The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved)" +} +variable "number_of_AZs" { + type = number + description = "Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter" + default = 2 +} +resource "null_resource" "availability_zones_validation1" { + count = var.number_of_AZs == length(var.availability_zones) ? 0 : "variable availability_zones list size must be equal to variable num_of_AZs" +} + +variable "gateways_subnets" { + type = list(string) + description = "Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} + +variable "transit_gateway_attachment_subnet_1_id" { + type = string + description = "The TGW attachment subnet ID located in the 1st Availability Zone" +} +variable "transit_gateway_attachment_subnet_2_id" { + type = string + description = "The TGW attachment subnet ID located in the 2st Availability Zone" +} +variable "transit_gateway_attachment_subnet_3_id" { + type = string + description = "The TGW attachment subnet ID located in the 3st Availability Zone" + default = "" +} +variable "transit_gateway_attachment_subnet_4_id" { + type = string + description = "The TGW attachment subnet ID located in the 4st Availability Zone" + default = "" +} +variable "nat_gw_subnet_1_cidr" { + type = string + description = "CIDR block for NAT subnet 1 located in the 1st Availability Zone" + default = "10.0.13.0/24" +} +variable "nat_gw_subnet_2_cidr" { + type = string + description = "CIDR block for NAT subnet 2 located in the 2st Availability Zone" + default = "10.0.23.0/24" +} +variable "nat_gw_subnet_3_cidr" { + type = string + description = "CIDR block for NAT subnet 3 located in the 3st Availability Zone" + default = "10.0.33.0/24" +} +variable "nat_gw_subnet_4_cidr" { + type = string + description = "CIDR block for NAT subnet 4 located in the 4st Availability Zone" + default = "10.0.43.0/24" +} +variable "gwlbe_subnet_1_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 1 located in the 1st Availability Zone" + default = "10.0.14.0/24" +} +variable "gwlbe_subnet_2_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 2 located in the 2st Availability Zone" + default = "10.0.24.0/24" +} +variable "gwlbe_subnet_3_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 3 located in the 3st Availability Zone" + default = "10.0.34.0/24" +} +variable "gwlbe_subnet_4_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 4 located in the 4st Availability Zone" + default = "10.0.44.0/24" +} +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." + default = "gwlb-management-server" +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + default = "gwlb-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + diff --git a/deprecated/terraform/aws/R80.40/tgw-gwlb/versions.tf b/deprecated/terraform/aws/R80.40/tgw-gwlb/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R80.40/tgw-gwlb/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/README.md b/deprecated/terraform/aws/R81/autoscale-gwlb/README.md new file mode 100755 index 00000000..fd28bd32 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/README.md @@ -0,0 +1,186 @@ +# Check Point CloudGuard Network Auto Scaling GWLB Terraform module for AWS + +Terraform module which deploys an Auto Scaling Group of Check Point Security Gateways into an existing VPC. + +These types of Terraform resources are supported: +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [Security group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) + + +See the [CloudGuard Auto Scaling for AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CloudGuard_Network_for_AWS_AutoScaling_DeploymentGuide/Topics-AWS-AutoScale-DG/Check-Point-CloudGuard-Network-for-AWS.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/autoscale/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "env1" + asg_name = "autoscaling_group" + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_ids = ["subnet-abc123", "subnet-def456"] + + // --- Automatic Provisioning with Security Management Server Settings --- + gateways_provision_address_type = "private" + allocate_public_IP = false + management_server = "mgmt_env1" + configuration_template = "tmpl_env1" + + // --- EC2 Instances Configuration --- + gateway_name = "asg_gateway" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + instances_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Auto Scaling Configuration --- + minimum_group_size = 2 + maximum_group_size = 10 + target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_instance_connect = false + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission +- To tear down your resources: + ``` + terraform destroy + ``` + + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|----------------------------|------------------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_ids | List of public subnet IDs to launch resources into. Recommended at least 2 | list(string) | n/a | n/a | yes | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_server | The name that represents the Security Management Server in the CME configuration | string | n/a | n/a | yes | +| configuration_template | Name of the provisioning template in the CME configuration | string | n/a | n/a | yes | +| gateway_name | The name tag of the Security Gateways instances | string | n/a | Check-Point-ASG-gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| instances_tags | (Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances | map(string) | n/a | {} | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| minimum_group_size | The minimum number of instances in the Auto Scaling group | number | n/a | 2 | no | +| maximum_group_size | The maximum number of instances in the Auto Scaling group | number | n/a | 10 | no | +| target_groups | (Optional) List of Target Group ARNs to associate with the Auto Scaling group | list(string) | n/a | [] | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters) | string | n/a | "12345678" | yes | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|------------------------------------------------|-------------------------------------------------------------------| +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_autoscaling_group_availability_zones | The AZs on which the Autoscaling Group is configured | +| autoscale_autoscaling_group_desired_capacity | The deployed AutoScaling Group's desired capacity of instances | +| autoscale_autoscaling_group_min_size | The deployed AutoScaling Group's minimum number of instances | +| autoscale_autoscaling_group_max_size | The deployed AutoScaling Group's maximum number of instances | +| autoscale_autoscaling_group_target_group_arns | The deployed AutoScaling Group's configured target groups | +| autoscale_autoscaling_group_subnets | The subnets on which the deployed AutoScaling Group is configured | +| autoscale_launch_template_id | The id of the Launch Template | +| autoscale_autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240417 | - Add support for Elastic Load Balancer Health Checks.
- EC2 Auto Scaling will start to detect and act on health checks performed by Elastic Load Balancing. | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point Auto Scaling GWLB Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/asg_userdata.yaml b/deprecated/terraform/aws/R81/autoscale-gwlb/asg_userdata.yaml new file mode 100755 index 00000000..bb095c01 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/asg_userdata.yaml @@ -0,0 +1,29 @@ +#cloud-config +network: + version: 1 + config: + - type: bridge + name: br0 + mtu: *eth0-mtu + subnets: + - address: *eth0-private + type: static + gateway: *default-gateway + dns_nameservers: + - *eth0-dns1 + bridge_interfaces: + - eth0 +kernel_parameters: + sim: + - sim_geneve_enabled=1 + - sim_geneve_br_dev=br0 + fw: + + - fwtls_bridge_mode_inspection=1 + - fw_geneve_enabled=1 +bootcmd: + - echo "brctl hairpin br0 eth0 on" >> /etc/rc.local + - echo "cpprod_util CPPROD_SetValue \"fw1\" \"AwsGwlb\" 4 1 1" >> /etc/rc.local +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" installationType=\"autoscale\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20231012\" templateName=\"autoscale_gwlb\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" bootstrapScript64=\"${BootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/locals.tf b/deprecated/terraform/aws/R81/autoscale-gwlb/locals.tf new file mode 100755 index 00000000..2c811532 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/locals.tf @@ -0,0 +1,55 @@ +locals { + asg_name = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.asg_name) + create_iam_role = var.enable_cloudwatch ? 1 : 0 + + gateways_provision_address_type_allowed_values = [ + "public", + "private" + ] + // Will fail if var.gateways_provision_address_type is invalid + validate_gateways_provision_address_type = index(local.gateways_provision_address_type_allowed_values, var.gateways_provision_address_type) + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh" + ] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SICKey] must be at least 8 alphanumeric characters" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + + tags_asg_format = null_resource.tags_as_list_of_maps.*.triggers + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) + gateway_password_hash_base64 = base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) + +} +resource "null_resource" "tags_as_list_of_maps" { + count = length(keys(var.instances_tags)) + + triggers = { + "key" = keys(var.instances_tags)[count.index] + "value" = values(var.instances_tags)[count.index] + "propagate_at_launch" = "true" + } +} diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/main.tf b/deprecated/terraform/aws/R81/autoscale-gwlb/main.tf new file mode 100755 index 00000000..67691dca --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/main.tf @@ -0,0 +1,202 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + version_license = var.gateway_version + amis_url = "https://cgi-cfts-staging.s3.amazonaws.com/utils/amis.yaml" + +} + +resource "aws_security_group" "permissive_sg" { + name_prefix = format("%s_PermissiveSecurityGroup", local.asg_name) + description = "Permissive security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + tags = { + Name = format("%s_PermissiveSecurityGroup", local.asg_name) + } +} + +resource "aws_launch_template" "asg_launch_template" { + name_prefix = local.asg_name + image_id = module.amis.ami_id + instance_type = var.gateway_instance_type + key_name = var.key_name + network_interfaces { + associate_public_ip_address = var.allocate_public_IP + security_groups = [aws_security_group.permissive_sg.id] + } + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + iam_instance_profile { + name = ( var.enable_cloudwatch ? aws_iam_instance_profile.instance_profile[0].name : "") + } + + monitoring { + enabled = true + } + + block_device_mappings { + device_name = "/dev/xvda" + ebs { + volume_type = var.volume_type + volume_size = var.volume_size + encrypted = var.enable_volume_encryption + } + } + + description = "Initial template version" + + user_data = base64encode(templatefile("${path.module}/asg_userdata.yaml", { + // script's arguments + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + EnableCloudWatch = var.enable_cloudwatch, + EnableInstanceConnect = var.enable_instance_connect, + Shell = var.admin_shell, + SICKey = local.gateway_SICkey_base64, + AllowUploadDownload = var.allow_upload_download, + BootstrapScript = local.gateway_bootstrap_script64, + OsVersion = local.version_split + })) +} +resource "aws_autoscaling_group" "asg" { + name_prefix = local.asg_name + launch_template { + id = aws_launch_template.asg_launch_template.id + version = aws_launch_template.asg_launch_template.latest_version + } + min_size = var.minimum_group_size + max_size = var.maximum_group_size + target_group_arns = var.target_groups + vpc_zone_identifier = var.subnet_ids + health_check_grace_period = 3600 + health_check_type = "ELB" + + tag { + key = "Name" + value = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.gateway_name) + propagate_at_launch = true + } + + tag { + key = "x-chkp-tags" + value = format("management=%s:template=%s:ip-address=%s", var.management_server, var.configuration_template, var.gateways_provision_address_type) + propagate_at_launch = true + } + + tag { + key = "x-chkp-topology" + value = "internal" + propagate_at_launch = true + } + + tag { + key = "x-chkp-solution" + value = "autoscale_gwlb" + propagate_at_launch = true + } + + dynamic "tag" { + for_each = var.instances_tags + content { + key = tag.key + value = tag.value + propagate_at_launch = true + } + } +} + +data "aws_iam_policy_document" "assume_role_policy_document" { + version = "2012-10-17" + statement { + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + effect = "Allow" + } +} + +resource "aws_iam_role" "role" { + count = local.create_iam_role + name_prefix = format("%s-iam_role", local.asg_name) + assume_role_policy = data.aws_iam_policy_document.assume_role_policy_document.json + path = "/" +} +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.create_iam_role + role = aws_iam_role.role[count.index].name + tag_name = local.asg_name +} +resource "aws_iam_instance_profile" "instance_profile" { + count = local.create_iam_role + name_prefix = format("%s-iam_instance_profile", local.asg_name) + path = "/" + role = aws_iam_role.role[count.index].name +} + +// Scaling metrics +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_low" { + alarm_name = format("%s_alarm_low", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-down if CPU < 60% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 60 + alarm_actions = [aws_autoscaling_policy.scale_down_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "LessThanThreshold" +} +resource "aws_autoscaling_policy" "scale_down_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_down", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = -1 +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_high" { + alarm_name = format("%s_alarm_high", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-up if CPU > 80% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 80 + alarm_actions = [aws_autoscaling_policy.scale_up_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "GreaterThanThreshold" +} +resource "aws_autoscaling_policy" "scale_up_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_up", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = 1 +} diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/output.tf b/deprecated/terraform/aws/R81/autoscale-gwlb/output.tf new file mode 100755 index 00000000..ce5f76ce --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/output.tf @@ -0,0 +1,41 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} + +output "autoscale_autoscaling_group_name" { + value = aws_autoscaling_group.asg.name +} +output "autoscale_autoscaling_group_arn" { + value = aws_autoscaling_group.asg.arn +} +output "autoscale_autoscaling_group_availability_zones" { + value = aws_autoscaling_group.asg.availability_zones +} +output "autoscale_autoscaling_group_desired_capacity" { + value = aws_autoscaling_group.asg.desired_capacity +} +output "autoscale_autoscaling_group_min_size" { + value = aws_autoscaling_group.asg.min_size +} +output "autoscale_autoscaling_group_max_size" { + value = aws_autoscaling_group.asg.max_size +} +output "autoscale_autoscaling_group_target_group_arns" { + value = aws_autoscaling_group.asg.target_group_arns +} +output "autoscale_autoscaling_group_subnets" { + value = aws_autoscaling_group.asg.vpc_zone_identifier +} + +output "autoscale_launch_template_id" { + value = aws_launch_template.asg_launch_template.id +} + +output "autoscale_security_group_id" { + value = aws_security_group.permissive_sg.id +} + +output "autoscale_iam_role_name" { + value = aws_iam_role.role.*.name +} + diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/terraform.tfvars b/deprecated/terraform/aws/R81/autoscale-gwlb/terraform.tfvars new file mode 100755 index 00000000..4cced958 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/terraform.tfvars @@ -0,0 +1,42 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "env1" +asg_name = "autoscaling_group" + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_ids = ["subnet-abc123", "subnet-def456"] + +// --- Automatic Provisioning with Security Management Server Settings --- +gateways_provision_address_type = "private" +allocate_public_IP = false +management_server = "mgmt_env1" +configuration_template = "tmpl_env1" + +// --- EC2 Instances Configuration --- +gateway_name = "asg_gateway" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +instances_tags = { + key1 = "value1" + key2 = "value2" +} +metadata_imdsv2_required = true + +// --- Auto Scaling Configuration --- +minimum_group_size = 2 +maximum_group_size = 10 +target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_instance_connect = false +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/variables.tf b/deprecated/terraform/aws/R81/autoscale-gwlb/variables.tf new file mode 100755 index 00000000..cb1a985c --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/variables.tf @@ -0,0 +1,191 @@ +// Module: Check Point CloudGuard Network Auto Scaling Group into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. Recommended at least 2" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the CME configuration" +} +variable "configuration_template" { + type = string + description = "Name of the provisioning template in the CME configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} + +// --- EC2 Instances Configuration --- +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateways instances" + default = "Check-Point-ASG-gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "instances_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances" + default = {} +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} + +// --- Auto Scaling Configuration --- +variable "minimum_group_size" { + type = number + description = "The minimum number of instances in the Auto Scaling group" + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximum number of instances in the Auto Scaling group" + default = 10 +} +variable "target_groups" { + type = list(string) + description = "(Optional) List of Target Group ARNs to associate with the Auto Scaling group" + default = [] +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} + +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/autoscale-gwlb/versions.tf b/deprecated/terraform/aws/R81/autoscale-gwlb/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale-gwlb/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/autoscale/README.md b/deprecated/terraform/aws/R81/autoscale/README.md new file mode 100755 index 00000000..5062ec5d --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/README.md @@ -0,0 +1,201 @@ +# Check Point CloudGuard Network Auto Scaling Terraform module for AWS + +Terraform module which deploys an Auto Scaling Group of Check Point Security Gateways into an existing VPC. + +These types of Terraform resources are supported: +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation +* [Proxy Elastic Load Balancer](https://www.terraform.io/docs/providers/aws/r/elb.html) - conditional creation + + +See the [CloudGuard Auto Scaling for AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CloudGuard_Network_for_AWS_AutoScaling_DeploymentGuide/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/autoscale/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "env1" + asg_name = "autoscaling_group" + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_ids = ["subnet-abc123", "subnet-def456"] + + // --- Automatic Provisioning with Security Management Server Settings --- + gateways_provision_address_type = "private" + management_server = "mgmt_env1" + configuration_template = "tmpl_env1" + + // --- EC2 Instances Configuration --- + gateway_name = "asg_gateway" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + instances_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Auto Scaling Configuration --- + minimum_group_size = 2 + maximum_group_size = 10 + target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_instance_connect = false + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Outbound Proxy Configuration (optional) --- + proxy_elb_type = "internet-facing" + proxy_elb_clients = "0.0.0.0/0" + proxy_elb_port = 8080 + ``` + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To create an ASG configuration without a proxy ELB: + ``` + proxy_elb_type= "none" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|----------------------------|----------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_ids | List of public subnet IDs to launch resources into. Recommended at least 2 | list(string) | n/a | n/a | yes | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| management_server | The name that represents the Security Management Server in the CME configuration | string | n/a | n/a | yes | +| configuration_template | Name of the provisioning template in the CME configuration | string | n/a | n/a | yes | +| gateway_name | The name tag of the Security Gateways instances | string | n/a | Check-Point-ASG-gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| instances_tags | (Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances | map(string) | n/a | {} | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| minimum_group_size | The minimum number of instances in the Auto Scaling group | number | n/a | 2 | no | +| maximum_group_size | The maximum number of instances in the Auto Scaling group | number | n/a | 10 | no | +| target_groups | (Optional) List of Target Group ARNs to associate with the Auto Scaling group | list(string) | n/a | [] | no | +| gateway_version | Gateway version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters) | string | n/a | "12345678" | yes | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| proxy_elb_type | Type of ELB to create as an HTTP/HTTPS outbound proxy | string | - none
- internal
- internet-facing | none | no | +| proxy_elb_port | The TCP port on which the proxy will be listening | number | n/a | 8080 | no | +| proxy_elb_clients | The CIDR range of the clients of the proxy | string | n/a | 0.0.0.0/0 | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|------------------------------------------------|-------------------------------------------------------------------| +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_autoscaling_group_availability_zones | The AZs on which the Autoscaling Group is configured | +| autoscale_autoscaling_group_desired_capacity | The deployed AutoScaling Group's desired capacity of instances | +| autoscale_autoscaling_group_min_size | The deployed AutoScaling Group's minimum number of instances | +| autoscale_autoscaling_group_max_size | The deployed AutoScaling Group's maximum number of instances | +| autoscale_autoscaling_group_load_balancers | The deployed AutoScaling Group's configured load balancers | +| autoscale_autoscaling_group_target_group_arns | The deployed AutoScaling Group's configured target groups | +| autoscale_autoscaling_group_subnets | The subnets on which the deployed AutoScaling Group is configured | +| autoscale_launch_template_id | The id of the Launch Template | +| autoscale_autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240417 | - Add support for Elastic Load Balancer Health Checks.
- EC2 Auto Scaling will start to detect and act on health checks performed by Elastic Load Balancing. | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | Change default shell for the admin user to /etc/cli.sh | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | AWS Terraform modules refactor | +| 20200318 | First release of Check Point Auto Scaling Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/autoscale/asg_userdata.yaml b/deprecated/terraform/aws/R81/autoscale/asg_userdata.yaml new file mode 100755 index 00000000..4c6633c3 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/asg_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" installationType=\"autoscale\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20240704\" templateName=\"autoscale\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" bootstrapScript64=\"${BootstrapScript}\" diff --git a/deprecated/terraform/aws/R81/autoscale/locals.tf b/deprecated/terraform/aws/R81/autoscale/locals.tf new file mode 100755 index 00000000..72fa5951 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/locals.tf @@ -0,0 +1,62 @@ +locals { + asg_name = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.asg_name) + create_iam_role = var.enable_cloudwatch ? 1 : 0 + + gateways_provision_address_type_allowed_values = [ + "public", + "private" + ] + // Will fail if var.gateways_provision_address_type is invalid + validate_gateways_provision_address_type = index(local.gateways_provision_address_type_allowed_values, var.gateways_provision_address_type) + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh" + ] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SICKey] must be at least 8 alphanumeric characters" + + proxy_elb_type_allowed_values = [ + "none", + "internal", + "internet-facing" + ] + // Will fail if var.proxy_elb_type is invalid + validate_proxy_elb_type = index(local.proxy_elb_type_allowed_values, var.proxy_elb_type) + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.proxy_elb_clients is invalid + regex_cidr_result = regex(local.regex_valid_cidr_range, var.proxy_elb_clients) == var.proxy_elb_clients ? 0 : "Variable [proxy_elb_clients] must be a valid CIDR range" + + tags_asg_format = null_resource.tags_as_list_of_maps.*.triggers + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_password_hash_base64 = base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) +} +resource "null_resource" "tags_as_list_of_maps" { + count = length(keys(var.instances_tags)) + + triggers = { + "key" = keys(var.instances_tags)[count.index] + "value" = values(var.instances_tags)[count.index] + "propagate_at_launch" = "true" + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/autoscale/main.tf b/deprecated/terraform/aws/R81/autoscale/main.tf new file mode 100755 index 00000000..68abbfe0 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/main.tf @@ -0,0 +1,248 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version +} + +resource "aws_security_group" "permissive_sg" { + name_prefix = format("%s_PermissiveSecurityGroup", local.asg_name) + description = "Permissive security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + tags = { + Name = format("%s_PermissiveSecurityGroup", local.asg_name) + } +} + +resource "aws_launch_template" "asg_launch_template" { + name_prefix = local.asg_name + image_id = module.amis.ami_id + instance_type = var.gateway_instance_type + key_name = var.key_name + network_interfaces { + associate_public_ip_address = true + security_groups = [aws_security_group.permissive_sg.id] + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + iam_instance_profile { + name = ( var.enable_cloudwatch ? aws_iam_instance_profile.instance_profile[0].name : "") + } + monitoring { + enabled = true + } + + block_device_mappings { + device_name = "/dev/xvda" + ebs { + volume_type = "gp3" + volume_size = var.volume_size + encrypted = var.enable_volume_encryption + } + } + description = "Initial template version" + + + user_data = base64encode(templatefile("${path.module}/asg_userdata.yaml", { + // script's arguments + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + EnableCloudWatch = var.enable_cloudwatch, + EnableInstanceConnect = var.enable_instance_connect, + Shell = var.admin_shell, + SICKey = local.gateway_SICkey_base64, + AllowUploadDownload = var.allow_upload_download, + BootstrapScript = local.gateway_bootstrap_script64, + OsVersion = local.version_split + })) +} +resource "aws_autoscaling_group" "asg" { + name_prefix = local.asg_name + launch_template { + id = aws_launch_template.asg_launch_template.id + version = aws_launch_template.asg_launch_template.latest_version + } + min_size = var.minimum_group_size + max_size = var.maximum_group_size + load_balancers = aws_elb.proxy_elb.*.name + target_group_arns = var.target_groups + vpc_zone_identifier = var.subnet_ids + health_check_grace_period = 3600 + health_check_type = "ELB" + + tag { + key = "Name" + value = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.gateway_name) + propagate_at_launch = true + } + + tag { + key = "x-chkp-tags" + value = format("management=%s:template=%s:ip-address=%s", var.management_server, var.configuration_template, var.gateways_provision_address_type) + propagate_at_launch = true + } + + dynamic "tag" { + for_each = var.instances_tags + content { + key = tag.key + value = tag.value + propagate_at_launch = true + } + } +} + +data "aws_iam_policy_document" "assume_role_policy_document" { + version = "2012-10-17" + statement { + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + effect = "Allow" + } +} + +resource "aws_iam_role" "role" { + count = local.create_iam_role + name_prefix = format("%s-iam_role", local.asg_name) + assume_role_policy = data.aws_iam_policy_document.assume_role_policy_document.json + path = "/" +} +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.create_iam_role + role = aws_iam_role.role[count.index].name + tag_name = local.asg_name +} + +resource "aws_iam_instance_profile" "instance_profile" { + count = local.create_iam_role + name_prefix = format("%s-iam_instance_profile", local.asg_name) + path = "/" + role = aws_iam_role.role[count.index].name +} + +// Proxy ELB +locals { + proxy_elb_condition = var.proxy_elb_type != "none" ? 1 : 0 +} +resource "random_id" "proxy_elb_uuid" { + byte_length = 5 +} +resource "aws_elb" "proxy_elb" { + count = local.proxy_elb_condition + name = format("%s-proxy-elb-%s", var.prefix, random_id.proxy_elb_uuid.hex) + internal = var.proxy_elb_type == "internal" + cross_zone_load_balancing = true + listener { + instance_port = var.proxy_elb_port + instance_protocol = "TCP" + lb_port = var.proxy_elb_port + lb_protocol = "TCP" + } + health_check { + target = format("TCP:%s", var.proxy_elb_port) + healthy_threshold = 3 + unhealthy_threshold = 5 + interval = 30 + timeout = 5 + } + subnets = var.subnet_ids + security_groups = [aws_security_group.elb_security_group[count.index].id] +} +resource "aws_load_balancer_policy" "proxy_elb_policy" { + count = local.proxy_elb_condition + load_balancer_name = aws_elb.proxy_elb[count.index].name + policy_name = "EnableProxyProtocol" + policy_type_name = "ProxyProtocolPolicyType" + + policy_attribute { + name = "ProxyProtocol" + value = "true" + } +} +resource "aws_security_group" "elb_security_group" { + count = local.proxy_elb_condition + description = "ELB security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + protocol = "tcp" + cidr_blocks = [var.proxy_elb_clients] + from_port = var.proxy_elb_port + to_port = var.proxy_elb_port + } +} + +// Scaling metrics +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_low" { + alarm_name = format("%s_alarm_low", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-down if CPU < 60% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 60 + alarm_actions = [aws_autoscaling_policy.scale_down_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "LessThanThreshold" +} +resource "aws_autoscaling_policy" "scale_down_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_down", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = -1 +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_high" { + alarm_name = format("%s_alarm_high", aws_autoscaling_group.asg.name) + metric_name = "CPUUtilization" + alarm_description = "Scale-up if CPU > 80% for 10 minutes" + namespace = "AWS/EC2" + statistic = "Average" + period = 300 + evaluation_periods = 2 + threshold = 80 + alarm_actions = [aws_autoscaling_policy.scale_up_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.asg.name + } + comparison_operator = "GreaterThanThreshold" +} +resource "aws_autoscaling_policy" "scale_up_policy" { + autoscaling_group_name = aws_autoscaling_group.asg.name + name = format("%s_scale_up", aws_autoscaling_group.asg.name) + adjustment_type = "ChangeInCapacity" + cooldown = 300 + scaling_adjustment = 1 +} diff --git a/deprecated/terraform/aws/R81/autoscale/output.tf b/deprecated/terraform/aws/R81/autoscale/output.tf new file mode 100755 index 00000000..152bb744 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/output.tf @@ -0,0 +1,43 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} + +output "autoscale_autoscaling_group_name" { + value = aws_autoscaling_group.asg.name +} +output "autoscale_autoscaling_group_arn" { + value = aws_autoscaling_group.asg.arn +} +output "autoscale_autoscaling_group_availability_zones" { + value = aws_autoscaling_group.asg.availability_zones +} +output "autoscale_autoscaling_group_desired_capacity" { + value = aws_autoscaling_group.asg.desired_capacity +} +output "autoscale_autoscaling_group_min_size" { + value = aws_autoscaling_group.asg.min_size +} +output "autoscale_autoscaling_group_max_size" { + value = aws_autoscaling_group.asg.max_size +} +output "autoscale_autoscaling_group_load_balancers" { + value = aws_autoscaling_group.asg.load_balancers +} +output "autoscale_autoscaling_group_target_group_arns" { + value = aws_autoscaling_group.asg.target_group_arns +} +output "autoscale_autoscaling_group_subnets" { + value = aws_autoscaling_group.asg.vpc_zone_identifier +} +output "autoscale_launch_template_id" { + value = aws_launch_template.asg_launch_template.id +} + +output "autoscale_security_group_id" { + value = aws_security_group.permissive_sg.id +} + +output "autoscale_iam_role_name" { + value = aws_iam_role.role.*.name +} + diff --git a/deprecated/terraform/aws/R81/autoscale/terraform.tfvars b/deprecated/terraform/aws/R81/autoscale/terraform.tfvars new file mode 100755 index 00000000..d513fcd5 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/terraform.tfvars @@ -0,0 +1,45 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "env1" +asg_name = "autoscaling_group" + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_ids = ["subnet-abc123", "subnet-def456"] + +// --- Automatic Provisioning with Security Management Server Settings --- +gateways_provision_address_type = "private" +management_server = "mgmt_env1" +configuration_template = "tmpl_env1" + +// --- EC2 Instances Configuration --- +gateway_name = "asg_gateway" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +instances_tags = { + key1 = "value1" + key2 = "value2" +} +metadata_imdsv2_required = true + +// --- Auto Scaling Configuration --- +minimum_group_size = 2 +maximum_group_size = 10 +target_groups = ["arn:aws:tg1/abc123", "arn:aws:tg2/def456"] + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_instance_connect = false +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Outbound Proxy Configuration (optional) --- +proxy_elb_type = "internet-facing" +proxy_elb_clients = "0.0.0.0/0" +proxy_elb_port = 8080 diff --git a/deprecated/terraform/aws/R81/autoscale/variables.tf b/deprecated/terraform/aws/R81/autoscale/variables.tf new file mode 100755 index 00000000..81d256ab --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/variables.tf @@ -0,0 +1,190 @@ +// Module: Check Point CloudGuard Network Auto Scaling Group into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. Recommended at least 2" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the CME configuration" +} +variable "configuration_template" { + type = string + description = "Name of the provisioning template in the CME configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} + +// --- EC2 Instances Configuration --- +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateways instances" + default = "Check-Point-ASG-gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "instances_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added on all AutoScaling Group instances" + default = {} +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} + +// --- Auto Scaling Configuration --- +variable "minimum_group_size" { + type = number + description = "The minimum number of instances in the Auto Scaling group" + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximum number of instances in the Auto Scaling group" + default = 10 +} +variable "target_groups" { + type = list(string) + description = "(Optional) List of Target Group ARNs to associate with the Auto Scaling group" + default = [] +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- (Optional) Outbound Proxy Configuration --- +variable "proxy_elb_type" { + type = string + description = "Type of ELB to create as an HTTP/HTTPS outbound proxy" + default = "none" +} +variable "proxy_elb_port" { + type = number + description = "The TCP port on which the proxy will be listening" + default = 8080 +} +variable "proxy_elb_clients" { + type = string + description = "The CIDR range of the clients of the proxy" + default = "0.0.0.0/0" +} diff --git a/deprecated/terraform/aws/R81/autoscale/versions.tf b/deprecated/terraform/aws/R81/autoscale/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/autoscale/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/cluster-master/README.md b/deprecated/terraform/aws/R81/cluster-master/README.md new file mode 100755 index 00000000..fb997341 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster-master/README.md @@ -0,0 +1,221 @@ +# Check Point CloudGuard Network Security Cluster Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cluster into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk104418) for additional information + +This solution uses the following modules: +- /terraform/aws/cluster +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/cluster-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + } + private_subnets_map = { + "us-east-1a" = 2 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint module.launch_cluster_into_vpc.aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|--------------------|-----------------------------------------------------| +| ami_id | The ami id of the deployed Security Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/cluster-master/locals.tf b/deprecated/terraform/aws/R81/cluster-master/locals.tf new file mode 100755 index 00000000..b77484fe --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster-master/locals.tf @@ -0,0 +1,52 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" +} diff --git a/deprecated/terraform/aws/R81/cluster-master/main.tf b/deprecated/terraform/aws/R81/cluster-master/main.tf new file mode 100755 index 00000000..29746863 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster-master/main.tf @@ -0,0 +1,64 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} +module "launch_cluster_into_vpc" { + source = "../cluster" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_id = module.launch_vpc.public_subnets_ids_list[0] + private_subnet_id = module.launch_vpc.private_subnets_ids_list[0] + private_route_table = aws_route_table.private_subnet_rtb.id + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + memberAToken = var.memberAToken + memberBToken = var.memberBToken + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp +} diff --git a/deprecated/terraform/aws/R81/cluster-master/output.tf b/deprecated/terraform/aws/R81/cluster-master/output.tf new file mode 100755 index 00000000..c1f47385 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster-master/output.tf @@ -0,0 +1,24 @@ +output "ami_id" { + value = module.launch_cluster_into_vpc.ami_id +} +output "cluster_public_ip" { + value = module.launch_cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.launch_cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.launch_cluster_into_vpc.member_b_public_ip +} +output "member_a_ssh" { + value = module.launch_cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.launch_cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.launch_cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.launch_cluster_into_vpc.member_b_url +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cluster-master/terraform.tfvars b/deprecated/terraform/aws/R81/cluster-master/terraform.tfvars new file mode 100755 index 00000000..1e7b2c78 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster-master/terraform.tfvars @@ -0,0 +1,47 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 +} +private_subnets_map = { + "us-east-1a" = 2 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cluster-master/variables.tf b/deprecated/terraform/aws/R81/cluster-master/variables.tf new file mode 100755 index 00000000..d1faf72c --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster-master/variables.tf @@ -0,0 +1,183 @@ +// Module: Check Point CloudGuard Network Security Cluster into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pairs. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R81/cluster-master/versions.tf b/deprecated/terraform/aws/R81/cluster-master/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/cluster/README.md b/deprecated/terraform/aws/R81/cluster/README.md new file mode 100755 index 00000000..4e6adbe2 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/README.md @@ -0,0 +1,202 @@ +# Check Point CloudGuard Network Security Cluster Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cluster into an existing VPC on AWS. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk104418) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_id = "subnet-123456" + private_subnet_id = "subnet-345678" + private_route_table = "rtb-12345678" + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|-----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the cluster. The cluster's public IPs will be generated from this subnet | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the cluster. The cluster's private IPs will be generated from this subnet | string | n/a | n/a | yes | +| private_route_table | (Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|--------------------|-----------------------------------------------------| +| ami_id | The ami id of the deployed Security Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240304 | Add x-chkp-cluster-ips, x-chkp-member-ips tags to cluster members | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Cluster Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/cluster/cluster_member_a_userdata.yaml b/deprecated/terraform/aws/R81/cluster/cluster_member_a_userdata.yaml new file mode 100755 index 00000000..1fa105c0 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/cluster_member_a_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenA}\"" installationType=\"cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" elasticIp=\"${MemberAPublicAddress}\" templateVersion=\"20240704\" templateName=\"cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" allocatePublicAddress=\"${AllocateAddress}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cluster/cluster_member_b_userdata.yaml b/deprecated/terraform/aws/R81/cluster/cluster_member_b_userdata.yaml new file mode 100755 index 00000000..36d29dc5 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/cluster_member_b_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenB}\"" installationType=\"cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" elasticIp=\"${MemberBPublicAddress}\" templateVersion=\"20231012\" templateName=\"cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" allocatePublicAddress=\"${AllocateAddress}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cluster/locals.tf b/deprecated/terraform/aws/R81/cluster/locals.tf new file mode 100755 index 00000000..d64b39e7 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/locals.tf @@ -0,0 +1,69 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + create_iam_role = var.predefined_role == "" ? 1 : 0 + provided_roue_table = var.private_route_table == "" ? 0 : 1 + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + //TokenA: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenA = split(" ", var.memberAToken) + tokenA_decode = base64decode(element(local.split_tokenA, length(local.split_tokenA)-1)) + regex_tokenA = regex(local.regex_token_valid, local.tokenA_decode) == local.tokenA_decode ? 0 : "Smart-1 Cloud token A is invalid format" + + //TokenB: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenB = split(" ", var.memberBToken) + tokenB_decode = base64decode(element(local.split_tokenB, length(local.split_tokenB)-1)) + regex_tokenB = regex(local.regex_token_valid, local.tokenB_decode) == local.tokenB_decode ? 0 : "Smart-1 Cloud token B is invalid format" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) + gateway_password_hash_base64=base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) +} diff --git a/deprecated/terraform/aws/R81/cluster/main.tf b/deprecated/terraform/aws/R81/cluster/main.tf new file mode 100755 index 00000000..8282b24b --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/main.tf @@ -0,0 +1,291 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +resource "aws_iam_instance_profile" "cluster_instance_profile" { + path = "/" + role = local.create_iam_role == 1 ? join("", module.cluster_iam_role.*.cluster_iam_role_name) : var.predefined_role +} + +module "cluster_iam_role" { + source = "../modules/cluster-iam-role" + count = local.create_iam_role +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_instance_profile.cluster_instance_profile.role + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name +} + +resource "aws_network_interface" "member_a_external_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A external" + source_dest_check = false + lifecycle { + ignore_changes = [private_ips_count,] + } + private_ips_count = 1 + tags = { + Name = format("%s-Member_A_ExternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_network_interface" "member_b_external_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B external" + source_dest_check = false + tags = { + Name = format("%s-Member_B_ExternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_network_interface" "member_a_internal_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A internal" + source_dest_check = false + lifecycle { + ignore_changes = [private_ips_count,] + } + private_ips_count = 1 + tags = { + Name = format("%s-Member_A_InternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_network_interface" "member_b_internal_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B internal" + source_dest_check = false + tags = { + Name = format("%s-Member_B_InternalInterface", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +resource "aws_route" "internal_default_route" { + count = local.internal_route_table_condition + route_table_id = var.private_route_table + lifecycle { + ignore_changes = [network_interface_id,] + } + destination_cidr_block = "0.0.0.0/0" + network_interface_id = aws_network_interface.member_a_internal_eni.id +} + +resource "aws_route_table_association" "private_rtb_to_private_subnet" { + count = var.private_route_table == "" ? 0 : 1 + route_table_id = var.private_route_table + subnet_id = var.private_subnet_id +} + +resource "aws_launch_template" "member_a_launch_template" { + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_a_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_a_internal_eni.id + device_index = 1 + } +} + +resource "aws_launch_template" "member_b_launch_template" { + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_b_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_b_internal_eni.id + device_index = 1 + } +} + +resource "aws_instance" "member-a-instance" { + depends_on = [ + aws_network_interface.member_a_external_eni, + aws_network_interface.member_a_internal_eni + ] + + launch_template { + id = aws_launch_template.member_a_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-A",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + var.allocate_and_associate_eip ? aws_eip.member_a_eip[0].public_ip : "", aws_network_interface.member_a_external_eni.private_ip,aws_network_interface.member_a_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:cluster-eth0-private-ip=%s:cluster-eth1-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0), + element(tolist(setsubtract(tolist(aws_network_interface.member_a_internal_eni.private_ips), [aws_network_interface.member_a_internal_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_a_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenA = var.memberAToken, + MemberAPublicAddress = var.allocate_and_associate_eip ? aws_eip.member_a_eip[0].public_ip : "", + AllocateAddress = var.allocate_and_associate_eip, + OsVersion = local.version_split + }) +} + +resource "aws_instance" "member-b-instance" { + depends_on = [ + aws_network_interface.member_b_external_eni, + aws_network_interface.member_b_internal_eni + ] + + launch_template { + id = aws_launch_template.member_b_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-B",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + var.allocate_and_associate_eip ? aws_eip.member_b_eip[0].public_ip : "", aws_network_interface.member_b_external_eni.private_ip,aws_network_interface.member_b_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:cluster-eth0-private-ip=%s:cluster-eth1-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0), + element(tolist(setsubtract(tolist(aws_network_interface.member_a_internal_eni.private_ips), [aws_network_interface.member_a_internal_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_b_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenB = var.memberBToken, + MemberBPublicAddress = var.allocate_and_associate_eip ? aws_eip.member_b_eip[0].public_ip : "", + AllocateAddress = var.allocate_and_associate_eip, + OsVersion = local.version_split + }) +} + +resource "aws_eip" "cluster_eip" { +} + +resource "aws_eip" "member_a_eip" { + count = var.allocate_and_associate_eip ? 1 : 0 +} + +resource "aws_eip" "member_b_eip" { + count = var.allocate_and_associate_eip ? 1 : 0 +} + +resource "aws_eip_association" "cluster_address_assoc" { + depends_on = [aws_instance.member-a-instance] + allocation_id = aws_eip.cluster_eip.id + lifecycle { + ignore_changes = [ + network_interface_id, private_ip_address + ] + } + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : ""//extracting member's secondary ip which represent the cluster ip +} +resource "aws_eip_association" "member_a_address_assoc" { + depends_on = [aws_instance.member-a-instance] + count = var.allocate_and_associate_eip ? 1 : 0 + allocation_id = aws_eip.member_a_eip[0].id + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = aws_network_interface.member_a_external_eni.private_ip //primary +} +resource "aws_eip_association" "member_b_address_assoc" { + depends_on = [aws_instance.member-b-instance] + count = var.allocate_and_associate_eip ? 1 : 0 + allocation_id = aws_eip.member_b_eip[0].id + network_interface_id = aws_network_interface.member_b_external_eni.id + private_ip_address = aws_network_interface.member_b_external_eni.private_ip //primary +} + diff --git a/deprecated/terraform/aws/R81/cluster/output.tf b/deprecated/terraform/aws/R81/cluster/output.tf new file mode 100755 index 00000000..6e8f5cbf --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/output.tf @@ -0,0 +1,24 @@ +output "ami_id" { + value = module.amis.ami_id +} +output "cluster_public_ip" { + value = aws_eip.cluster_eip.*.public_ip +} +output "member_a_public_ip" { + value = aws_eip.member_a_eip.*.public_ip +} +output "member_b_public_ip" { + value = aws_eip.member_b_eip.*.public_ip +} +output "member_a_ssh" { + value = var.allocate_and_associate_eip ? format("ssh -i %s admin@%s", var.key_name, aws_eip.member_a_eip[0].public_ip) : "" +} +output "member_b_ssh" { + value = var.allocate_and_associate_eip ? format("ssh -i %s admin@%s", var.key_name, aws_eip.member_b_eip[0].public_ip) : "" +} +output "member_a_url" { + value = var.allocate_and_associate_eip ? format("https://%s", aws_eip.member_a_eip[0].public_ip) : "" +} +output "member_b_url" { + value = var.allocate_and_associate_eip ? format("https://%s", aws_eip.member_b_eip[0].public_ip) : "" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cluster/terraform.tfvars b/deprecated/terraform/aws/R81/cluster/terraform.tfvars new file mode 100755 index 00000000..179fe10b --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_id = "subnet-123456" +private_subnet_id = "subnet-345678" +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cluster/variables.tf b/deprecated/terraform/aws/R81/cluster/variables.tf new file mode 100755 index 00000000..1b515744 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/variables.tf @@ -0,0 +1,181 @@ +// Module: Check Point CloudGuard Network Security Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_id" { + type = string + description = "The public subnet of the cluster. The cluster's public IPs will be generated from this subnet" +} +variable "private_subnet_id" { + type = string + description = "The private subnet of the cluster. The cluster's private IPs will be generated from this subnet" +} +variable "private_route_table" { + type = string + description = "(Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Single AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R81/cluster/versions.tf b/deprecated/terraform/aws/R81/cluster/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/cluster/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/cme-iam-role-gwlb/README.md b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/README.md new file mode 100755 index 00000000..ae261614 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/README.md @@ -0,0 +1,100 @@ +# AWS IAM Role for Cloud Management Extension (CME) manages Gateway Load Balancer Auto Scale Group Terraform module + +Terraform module which creates an AWS IAM Role for Cloud Management Extension (CME) manages Gateway Load Balancer Auto Scale Group on Security Management Server. + +These types of Terraform resources are supported: +* [AWS IAM role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) +* [AWS IAM policy](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_policy) +* [AWS IAM policy attachment](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role_policy_attachment) + +This type of Terraform data source is supported: +* [AWS IAM policy document](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/iam_policy_document) + +See the [Creating an AWS IAM Role for Security Management Server](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk122074) for additional information + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cme-iam-role-gwlb/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cme-iam-role-gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cme-iam-role-gwlb/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + permissions = "Create with read permissions" + sts_roles = ['arn:aws:iam::111111111111:role/role_name'] + trusted_account = "" + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-----------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| permissions | The IAM role permissions | string | - Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| sts_roles | The IAM role will be able to assume these STS Roles (map of string ARNs) | list(string) | n/a | [] | no | +| trusted_account | A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|----------------------|---------------------------------------| +| cme_iam_role_arn | The created AWS IAM Role arn | +| cme_iam_role_name | The created AWS IAM Role name | +| cme_iam_profile_name | The created AWS instance profile name | +| cme_iam_profile_arn | The created AWS instance profile arn | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|--------------------------------------------------------------------| +| 20240507 | Add ec2:DescribeRegions read permission to the IAM role policy | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230926 | CME instance profile for IAM Role | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/cme-iam-role-gwlb/main.tf b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/main.tf new file mode 100755 index 00000000..33ea37ab --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/main.tf @@ -0,0 +1,110 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +resource "aws_iam_role" "cme_iam_role_gwlb" { + assume_role_policy = data.aws_iam_policy_document.cme_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "cme_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = var.trusted_account == "" ? "Service" : "AWS" + identifiers = var.trusted_account == "" ? ["ec2.amazonaws.com"] : [var.trusted_account] + } + } +} + +locals { + provided_sts_roles = length(var.sts_roles) == 0 ? 0 : 1 + allow_read_permissions = var.permissions == "Create with read-write permissions" || var.permissions == "Create with read permissions" ? 1 : 0 + allow_write_permissions = var.permissions == "Create with read-write permissions" ? 1 : 0 +} + +data "aws_iam_policy_document" "cme_role_sts_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + resources = var.sts_roles + } +} +resource "aws_iam_policy" "cme_role_sts_policy" { + count = local.provided_sts_roles + policy = data.aws_iam_policy_document.cme_role_sts_policy_doc.json + +} +resource "aws_iam_role_policy_attachment" "attach_sts_policy" { + count = local.provided_sts_roles + policy_arn = aws_iam_policy.cme_role_sts_policy[0].arn + role = aws_iam_role.cme_iam_role_gwlb.id +} + +data "aws_iam_policy_document" "cme_role_read_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "autoscaling:DescribeAutoScalingGroups", + "ec2:DescribeRegions", + "ec2:DescribeInstances", + "ec2:DescribeNetworkInterfaces", + "ec2:DescribeRouteTables", + "ec2:DescribeSecurityGroups", + "ec2:DescribeSubnets", + "ec2:DescribeVpcs", + "ec2:DescribeInternetGateways", + "ec2:DescribeVpcEndpoints", + "ec2:DescribeVpcEndpointServiceConfigurations", + "elasticloadbalancing:DescribeLoadBalancers", + "elasticloadbalancing:DescribeTags", + "elasticloadbalancing:DescribeListeners", + "elasticloadbalancing:DescribeTargetGroups", + "elasticloadbalancing:DescribeRules", + "elasticloadbalancing:DescribeTargetHealth"] + resources = ["*"] + } +} +resource "aws_iam_policy" "cme_role_read_policy" { + count = local.allow_read_permissions + policy = data.aws_iam_policy_document.cme_role_read_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_read_policy" { + count = local.allow_read_permissions + policy_arn = aws_iam_policy.cme_role_read_policy[0].arn + role = aws_iam_role.cme_iam_role_gwlb.id +} + +data "aws_iam_policy_document" "cme_role_write_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "ec2:CreateRoute", + "ec2:ReplaceRoute", + "ec2:DeleteRoute", + "ec2:CreateRouteTable", + "ec2:AssociateRouteTable", + "ec2:CreateTags" +] + resources = ["*"] + } +} +resource "aws_iam_policy" "cme_role_write_policy" { + count = local.allow_write_permissions + policy = data.aws_iam_policy_document.cme_role_write_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_write_policy" { + count = local.allow_write_permissions + policy_arn = aws_iam_policy.cme_role_write_policy[0].arn + role = aws_iam_role.cme_iam_role_gwlb.id +} +resource "aws_iam_instance_profile" "iam_instance_profile" { + role = aws_iam_role.cme_iam_role_gwlb.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cme-iam-role-gwlb/output.tf b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/output.tf new file mode 100755 index 00000000..8c86901a --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/output.tf @@ -0,0 +1,13 @@ +output "cme_iam_role_arn" { + value = aws_iam_role.cme_iam_role_gwlb.arn +} +output "cme_iam_role_name" { + value = aws_iam_role.cme_iam_role_gwlb.name +} +output "cme_iam_profile_name" { + value = aws_iam_instance_profile.iam_instance_profile.name +} +output "cme_iam_profile_arn" { + value = aws_iam_instance_profile.iam_instance_profile.arn +} + diff --git a/deprecated/terraform/aws/R81/cme-iam-role-gwlb/terraform.tfvars b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/terraform.tfvars new file mode 100755 index 00000000..9914eae9 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/terraform.tfvars @@ -0,0 +1,5 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +permissions = "Create with read permissions" +sts_roles = [] +trusted_account = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cme-iam-role-gwlb/variables.tf b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/variables.tf new file mode 100755 index 00000000..3a0fe740 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/variables.tf @@ -0,0 +1,42 @@ +// Module: IAM role for selected permissions + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +variable "permissions" { + type = string + description = "The IAM role permissions" + default = "Create with read permissions" +} +locals { + permissions_allowed_values = [ + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.permissions) +} +variable "sts_roles" { + type = list(string) + description = "The IAM role will be able to assume these STS Roles (map of string ARNs)" + default = [] +} +variable "trusted_account" { + type = string + description = "A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it" + default = "" +} diff --git a/deprecated/terraform/aws/R81/cme-iam-role-gwlb/versions.tf b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/versions.tf new file mode 100755 index 00000000..b3e24059 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role-gwlb/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/cme-iam-role/README.md b/deprecated/terraform/aws/R81/cme-iam-role/README.md new file mode 100755 index 00000000..5aa02a68 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role/README.md @@ -0,0 +1,102 @@ +# AWS IAM Role for Cloud Management Extension (CME) Terraform module + +Terraform module which creates an AWS IAM Role for Cloud Management Extension (CME) on Security Management Server. + +These types of Terraform resources are supported: +* [AWS IAM role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) +* [AWS IAM policy](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_policy) +* [AWS IAM policy attachment](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role_policy_attachment) + +This type of Terraform data source is supported: +* [AWS IAM policy document](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/iam_policy_document) + +See the [Creating an AWS IAM Role for Security Management Server](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk122074) for additional information + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cme-iam-role/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cme-iam-role/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cme-iam-role/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + permissions = "Create with read permissions" + sts_roles = ['arn:aws:iam::111111111111:role/role_name'] + trusted_account = "" + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-----------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| permissions | The IAM role permissions | string | - Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| sts_roles | The IAM role will be able to assume these STS Roles (map of string ARNs) | list(string) | n/a | [] | no | +| trusted_account | A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|----------------------|---------------------------------------| +| cme_iam_role_arn | The created AWS IAM Role arn | +| cme_iam_role_name | The created AWS IAM Role name | +| cme_iam_profile_name | The created AWS instance profile name | +| cme_iam_profile_arn | The created AWS instance profile arn | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|--------------------------------------------------------------------| +| 20240507 | Add ec2:DescribeRegions read permission to the IAM role policy | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230514 | CME instance profile for IAM Role | +| 20210309 | First release of Check Point CME IAM Role Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/cme-iam-role/main.tf b/deprecated/terraform/aws/R81/cme-iam-role/main.tf new file mode 100755 index 00000000..817e3b90 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role/main.tf @@ -0,0 +1,136 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +resource "aws_iam_role" "cme_iam_role" { + assume_role_policy = data.aws_iam_policy_document.cme_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "cme_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = var.trusted_account == "" ? "Service" : "AWS" + identifiers = var.trusted_account == "" ? ["ec2.amazonaws.com"] : [var.trusted_account] + } + } +} + +locals { + provided_sts_roles = length(var.sts_roles) == 0 ? 0 : 1 + allow_read_permissions = var.permissions == "Create with read-write permissions" || var.permissions == "Create with read permissions" ? 1 : 0 + allow_write_permissions = var.permissions == "Create with read-write permissions" ? 1 : 0 +} + +data "aws_iam_policy_document" "cme_role_sts_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + resources = var.sts_roles + } +} +resource "aws_iam_policy" "cme_role_sts_policy" { + count = local.provided_sts_roles + policy = data.aws_iam_policy_document.cme_role_sts_policy_doc.json + +} +resource "aws_iam_role_policy_attachment" "attach_sts_policy" { + count = local.provided_sts_roles + policy_arn = aws_iam_policy.cme_role_sts_policy[0].arn + role = aws_iam_role.cme_iam_role.id +} + +data "aws_iam_policy_document" "cme_role_read_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "autoscaling:DescribeAutoScalingGroups", + "ec2:DescribeRegions", + "ec2:DescribeCustomerGateways", + "ec2:DescribeInstances", + "ec2:DescribeNetworkInterfaces", + "ec2:DescribeRouteTables", + "ec2:DescribeSecurityGroups", + "ec2:DescribeSubnets", + "ec2:DescribeTransitGateways", + "ec2:DescribeTransitGatewayAttachments", + "ec2:DescribeTransitGatewayRouteTables", + "ec2:DescribeVpcs", + "ec2:DescribeVpnGateways", + "ec2:DescribeVpnConnections", + "ec2:GetTransitGatewayAttachmentPropagations", + "elasticloadbalancing:DescribeLoadBalancers", + "elasticloadbalancing:DescribeTags", + "elasticloadbalancing:DescribeListeners", + "elasticloadbalancing:DescribeTargetGroups", + "elasticloadbalancing:DescribeRules", + "elasticloadbalancing:DescribeTargetHealth"] + resources = ["*"] + } +} +resource "aws_iam_policy" "cme_role_read_policy" { + count = local.allow_read_permissions + policy = data.aws_iam_policy_document.cme_role_read_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_read_policy" { + count = local.allow_read_permissions + policy_arn = aws_iam_policy.cme_role_read_policy[0].arn + role = aws_iam_role.cme_iam_role.id +} + +data "aws_iam_policy_document" "cme_role_write_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "ec2:AssociateTransitGatewayRouteTable", + "ec2:AttachVpnGateway", + "ec2:CreateCustomerGateway", + "ec2:CreateVpnConnection", + "ec2:CreateVpnGateway", + "ec2:DeleteCustomerGateway", + "ec2:DeleteVpnConnection", + "ec2:DeleteVpnGateway", + "ec2:DetachVpnGateway", + "ec2:DisableTransitGatewayRouteTablePropagation", + "ec2:DisableVgwRoutePropagation", + "ec2:DisassociateTransitGatewayRouteTable", + "ec2:EnableTransitGatewayRouteTablePropagation", + "ec2:EnableVgwRoutePropagation"] + resources = ["*"] + } + statement { + effect = "Allow" + actions = [ + "cloudformation:DescribeStacks", + "cloudformation:DescribeStackResources", + "cloudformation:ListStacks"] + resources = ["*"] + } + statement { + effect = "Allow" + actions = [ + "cloudformation:CreateStack", + "cloudformation:DeleteStack"] + resources = ["arn:aws:cloudformation:*:*:stack/vpn-by-tag--*/*"] + } +} +resource "aws_iam_policy" "cme_role_write_policy" { + count = local.allow_write_permissions + policy = data.aws_iam_policy_document.cme_role_write_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_write_policy" { + count = local.allow_write_permissions + policy_arn = aws_iam_policy.cme_role_write_policy[0].arn + role = aws_iam_role.cme_iam_role.id +} +resource "aws_iam_instance_profile" "iam_instance_profile" { + role = aws_iam_role.cme_iam_role.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cme-iam-role/output.tf b/deprecated/terraform/aws/R81/cme-iam-role/output.tf new file mode 100755 index 00000000..cad35709 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role/output.tf @@ -0,0 +1,12 @@ +output "cme_iam_role_arn" { + value = aws_iam_role.cme_iam_role.arn +} +output "cme_iam_role_name" { + value = aws_iam_role.cme_iam_role.name +} +output "cme_iam_profile_name" { + value = aws_iam_instance_profile.iam_instance_profile.name +} +output "cme_iam_profile_arn" { + value = aws_iam_instance_profile.iam_instance_profile.arn +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cme-iam-role/terraform.tfvars b/deprecated/terraform/aws/R81/cme-iam-role/terraform.tfvars new file mode 100755 index 00000000..9914eae9 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role/terraform.tfvars @@ -0,0 +1,5 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +permissions = "Create with read permissions" +sts_roles = [] +trusted_account = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cme-iam-role/variables.tf b/deprecated/terraform/aws/R81/cme-iam-role/variables.tf new file mode 100755 index 00000000..3a0fe740 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role/variables.tf @@ -0,0 +1,42 @@ +// Module: IAM role for selected permissions + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +variable "permissions" { + type = string + description = "The IAM role permissions" + default = "Create with read permissions" +} +locals { + permissions_allowed_values = [ + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.permissions) +} +variable "sts_roles" { + type = list(string) + description = "The IAM role will be able to assume these STS Roles (map of string ARNs)" + default = [] +} +variable "trusted_account" { + type = string + description = "A 12 digits number that represents the ID of a trusted account. IAM users in this account will be able assume the IAM role and receive the permissions attached to it" + default = "" +} diff --git a/deprecated/terraform/aws/R81/cme-iam-role/versions.tf b/deprecated/terraform/aws/R81/cme-iam-role/versions.tf new file mode 100755 index 00000000..b3e24059 --- /dev/null +++ b/deprecated/terraform/aws/R81/cme-iam-role/versions.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/cross-az-cluster-master/README.md b/deprecated/terraform/aws/R81/cross-az-cluster-master/README.md new file mode 100755 index 00000000..7ab3bd65 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster-master/README.md @@ -0,0 +1,219 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster into into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/cross-az-cluster +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cross-az-cluster-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cross-az-cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cross-az-cluster: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cross-az-cluster-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/cross-az-cluster-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + private_subnets_map = { + "us-east-1a" = 3 + "us-east-1a" = 4 + } + subnets_bit_length = 8 + + + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create IAM Role: + ``` + predefined_role = "" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint module.launch_cluster_into_vpc.aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1 \"us-east-1b\" = 2} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3 \"us-east-1b\" = 4} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX - R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|--------------------|--------------------------------------------------------------| +| ami_id | The ami id of the deployed Security Cross AZ Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221123 | R81.20 version support | +| 20221123 | Changed default version and added instances types | +| 20221123 | First release of Check Point Security Cross AZ Cluster Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../cross-az/LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/cross-az-cluster-master/locals.tf b/deprecated/terraform/aws/R81/cross-az-cluster-master/locals.tf new file mode 100755 index 00000000..68e4523f --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster-master/locals.tf @@ -0,0 +1,58 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R81/cross-az-cluster-master/main.tf b/deprecated/terraform/aws/R81/cross-az-cluster-master/main.tf new file mode 100755 index 00000000..f12ae536 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster-master/main.tf @@ -0,0 +1,70 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets_a" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} +resource "aws_route_table_association" "private_rtb_to_private_subnets_b" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[1] +} + +module "launch_cluster_into_vpc" { + source = "../cross-az-cluster" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_ids = module.launch_vpc.public_subnets_ids_list + private_subnet_ids = module.launch_vpc.private_subnets_ids_list + private_route_table = aws_route_table.private_subnet_rtb.id + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + memberAToken = var.memberAToken + memberBToken = var.memberBToken + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + volume_type = var.volume_type +} diff --git a/deprecated/terraform/aws/R81/cross-az-cluster-master/output.tf b/deprecated/terraform/aws/R81/cross-az-cluster-master/output.tf new file mode 100755 index 00000000..c1f47385 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster-master/output.tf @@ -0,0 +1,24 @@ +output "ami_id" { + value = module.launch_cluster_into_vpc.ami_id +} +output "cluster_public_ip" { + value = module.launch_cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.launch_cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.launch_cluster_into_vpc.member_b_public_ip +} +output "member_a_ssh" { + value = module.launch_cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.launch_cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.launch_cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.launch_cluster_into_vpc.member_b_url +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cross-az-cluster-master/terraform.tfvars b/deprecated/terraform/aws/R81/cross-az-cluster-master/terraform.tfvars new file mode 100755 index 00000000..28cb64a3 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster-master/terraform.tfvars @@ -0,0 +1,48 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cross-az-cluster-master/variables.tf b/deprecated/terraform/aws/R81/cross-az-cluster-master/variables.tf new file mode 100755 index 00000000..d49cf50c --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster-master/variables.tf @@ -0,0 +1,183 @@ +// Module: Check Point CloudGuard Network Security Cross AZ Cluster into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1 \"us-east-1b\" = 2} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3 \"us-east-1b\" = 4} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R81/cross-az-cluster-master/versions.tf b/deprecated/terraform/aws/R81/cross-az-cluster-master/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/README.md b/deprecated/terraform/aws/R81/cross-az-cluster/README.md new file mode 100755 index 00000000..9e5b3c7e --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/README.md @@ -0,0 +1,196 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster into an existing VPC on AWS. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cross-az-cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cross-az-cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/cross-az-cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_ids = ["subnet-abc123", "subnet-def456"] + private_subnet_ids = ["subnet-abc234", "subnet-def567"] + private_route_table = "rtb-12345678" + + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_ids | List of public subnet IDs to launch resources into. At least 2 | list(string) | n/a | n/a | yes | +| private_subnet_ids | List of private subnet IDs to launch resources into. At least 2 | list(string) | n/a | n/a | yes | | +| private_route_table | (Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX - R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------|--------------------------------------------------------------| +| ami_id | The ami id of the deployed Security Cross AZ Cluster members | +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240304 | Add x-chkp-cluster-ips, x-chkp-member-ips tags to cluster members | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221123 | R81.20 version support | +| 20221123 | Changed default version and added instances types | +| 20221123 | First release of Check Point Security Cross AZ Cluster Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../../cross-az/LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_a_userdata.yaml b/deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_a_userdata.yaml new file mode 100755 index 00000000..f9a926c5 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_a_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenA}\"" installationType=\"cross-az-cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20240310\" templateName=\"cross_az_cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" elasticIp=\"${MemberAPublicAddress}\" otherMemberIp=\"${MemberBPrivateAddressCluster}\" clusterIp=\"${PublicAddressCluster}\" secondaryIp=\"${MemberAPrivateAddressSecondary}\" otherMemberPrivateClusterIp=\"${MemberBPrivateAddressSecondary}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_b_userdata.yaml b/deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_b_userdata.yaml new file mode 100755 index 00000000..a374aaa6 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/cluster_member_b_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenB}\"" installationType=\"cross-az-cluster\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20240310\" templateName=\"cross_az_cluster\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname}\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" elasticIp=\"${MemberBPublicAddress}\" otherMemberIp=\"${MemberAPrivateAddressCluster}\" clusterIp=\"${PublicAddressCluster}\" secondaryIp=\"${MemberBPrivateAddressSecondary}\" otherMemberPrivateClusterIp=\"${MemberAPrivateAddressSecondary}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/locals.tf b/deprecated/terraform/aws/R81/cross-az-cluster/locals.tf new file mode 100755 index 00000000..19f67f30 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/locals.tf @@ -0,0 +1,75 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + create_iam_role = var.predefined_role == "" ? 1 : 0 + provided_roue_table = var.private_route_table == "" ? 0 : 1 + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + //TokenA: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenA = split(" ", var.memberAToken) + tokenA_decode = base64decode(element(local.split_tokenA, length(local.split_tokenA)-1)) + regex_tokenA = regex(local.regex_token_valid, local.tokenA_decode) == local.tokenA_decode ? 0 : "Smart-1 Cloud token A is invalid format" + + //TokenB: will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_tokenB = split(" ", var.memberBToken) + tokenB_decode = base64decode(element(local.split_tokenB, length(local.split_tokenB)-1)) + regex_tokenB = regex(local.regex_token_valid, local.tokenB_decode) == local.tokenB_decode ? 0 : "Smart-1 Cloud token B is invalid format" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64=base64encode(var.gateway_SICKey) + gateway_password_hash_base64=base64encode(var.gateway_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/main.tf b/deprecated/terraform/aws/R81/cross-az-cluster/main.tf new file mode 100755 index 00000000..d6a3bda3 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/main.tf @@ -0,0 +1,294 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +resource "aws_iam_instance_profile" "cluster_instance_profile" { + path = "/" + role = local.create_iam_role == 1 ? join("", module.cluster_iam_role.*.cluster_iam_role_name) : var.predefined_role +} + +module "cluster_iam_role" { + source = "../modules/cluster-iam-role" + count = local.create_iam_role +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_instance_profile.cluster_instance_profile.role + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name +} + +resource "aws_network_interface" "member_a_external_eni" { + subnet_id = var.public_subnet_ids[0] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A external" + source_dest_check = false + private_ips_count = 1 + tags = { + x-chkp-interface-type = "external" } +} + +resource "aws_network_interface" "member_b_external_eni" { + subnet_id = var.public_subnet_ids[1] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B external" + source_dest_check = false + private_ips_count = 1 + tags = { + x-chkp-interface-type = "external" } +} + +resource "aws_network_interface" "member_a_internal_eni" { + subnet_id = var.private_subnet_ids[0] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member A internal" + source_dest_check = false + tags = { + x-chkp-interface-type = "internal" } +} + +resource "aws_network_interface" "member_b_internal_eni" { + subnet_id = var.private_subnet_ids[1] + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "Member B internal" + source_dest_check = false + tags = { + x-chkp-interface-type = "internal" } +} + +resource "aws_route" "internal_default_route" { + count = local.internal_route_table_condition + route_table_id = var.private_route_table + lifecycle { + ignore_changes = [network_interface_id,] + } + destination_cidr_block = "0.0.0.0/0" + network_interface_id = aws_network_interface.member_a_internal_eni.id +} + +resource "aws_route_table_association" "private_rtb_a" { + count = var.private_route_table == "" ? 0 : 1 + route_table_id = var.private_route_table + subnet_id = var.private_subnet_ids[0] +} +resource "aws_route_table_association" "private_rtb_b" { + count = var.private_route_table == "" ? 0 : 1 + route_table_id = var.private_route_table + subnet_id = var.private_subnet_ids[1] +} + +resource "aws_launch_template" "member_a_launch_template" { + depends_on = [ + aws_network_interface.member_a_external_eni, + aws_network_interface.member_a_internal_eni + ] + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_a_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_a_internal_eni.id + device_index = 1 + } +} + +resource "aws_launch_template" "member_b_launch_template" { + depends_on = [ + aws_network_interface.member_b_external_eni, + aws_network_interface.member_b_internal_eni + ] + instance_type = var.gateway_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = aws_iam_instance_profile.cluster_instance_profile.id + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.member_b_external_eni.id + device_index = 0 + } + network_interfaces { + network_interface_id = aws_network_interface.member_b_internal_eni.id + device_index = 1 + } +} + +resource "aws_instance" "member-a-instance" { + depends_on = [ + aws_launch_template.member_a_launch_template + ] + + launch_template { + id = aws_launch_template.member_a_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-A",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + aws_eip.member_a_eip.public_ip, aws_network_interface.member_a_external_eni.private_ip,aws_network_interface.member_a_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:secondary-external-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_a_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenA = var.memberAToken, + MemberAPublicAddress = aws_eip.member_a_eip.public_ip, + PublicAddressCluster = aws_eip.cluster_eip.public_ip, + MemberAPrivateAddressSecondary = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : "",//extracting member's secondary ip which represent the cluster ip + MemberBPrivateAddressCluster = aws_network_interface.member_b_internal_eni.private_ip, + MemberBPrivateAddressSecondary = length(tolist(aws_network_interface.member_b_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_b_external_eni.private_ips), [aws_network_interface.member_b_external_eni.private_ip])), 0) : "", + AllocateAddress = true, + OsVersion = local.version_split + }) +} + +resource "aws_instance" "member-b-instance" { + depends_on = [ + aws_launch_template.member_b_launch_template + ] + + launch_template { + id = aws_launch_template.member_b_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = format("%s-Member-B",var.gateway_name), + x-chkp-member-ips = format("public-ip=%s:external-private-ip=%s:internal-private-ip=%s", + aws_eip.member_b_eip.public_ip, aws_network_interface.member_b_external_eni.private_ip,aws_network_interface.member_b_internal_eni.private_ip), + x-chkp-cluster-ips = format("cluster-ip=%s:secondary-external-private-ip=%s", + aws_eip.cluster_eip.public_ip, element(tolist(setsubtract(tolist(aws_network_interface.member_b_external_eni.private_ips), [aws_network_interface.member_b_external_eni.private_ip])), 0)) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/cluster_member_b_userdata.yaml", { + // script's arguments + Hostname = var.gateway_hostname, + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + EnableInstanceConnect = var.enable_instance_connect, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + SICKey = local.gateway_SICkey_base64, + TokenB = var.memberBToken, + MemberBPublicAddress = aws_eip.member_b_eip.public_ip, + PublicAddressCluster=aws_eip.cluster_eip.public_ip, + MemberBPrivateAddressSecondary = length(tolist(aws_network_interface.member_b_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_b_external_eni.private_ips), [aws_network_interface.member_b_external_eni.private_ip])), 0) : "", //extracting member's secondary ip which represent the member ip + MemberAPrivateAddressCluster=aws_network_interface.member_a_internal_eni.private_ip, + MemberAPrivateAddressSecondary = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : "", + AllocateAddress = true, + OsVersion = local.version_split + }) +} + +resource "aws_eip" "cluster_eip" { +} +resource "aws_eip" "member_a_eip" { +} +resource "aws_eip" "member_b_eip" { +} + +resource "aws_eip_association" "cluster_address_assoc" { + depends_on = [aws_instance.member-a-instance] + allocation_id = aws_eip.cluster_eip.id + lifecycle { + ignore_changes = [ + network_interface_id, private_ip_address + ] + } + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = length(tolist(aws_network_interface.member_a_external_eni.private_ips)) > 1 ? element(tolist(setsubtract(tolist(aws_network_interface.member_a_external_eni.private_ips), [aws_network_interface.member_a_external_eni.private_ip])), 0) : ""//extracting member's secondary ip which represent the cluster ip +} +resource "aws_eip_association" "member_a_address_assoc" { + depends_on = [aws_instance.member-a-instance] + allocation_id = aws_eip.member_a_eip.id + network_interface_id = aws_network_interface.member_a_external_eni.id + private_ip_address = aws_network_interface.member_a_external_eni.private_ip //primary +} +resource "aws_eip_association" "member_b_address_assoc" { + depends_on = [aws_instance.member-b-instance] + allocation_id = aws_eip.member_b_eip.id + network_interface_id = aws_network_interface.member_b_external_eni.id + private_ip_address = aws_network_interface.member_b_external_eni.private_ip //primary +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/output.tf b/deprecated/terraform/aws/R81/cross-az-cluster/output.tf new file mode 100755 index 00000000..e475a650 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/output.tf @@ -0,0 +1,30 @@ +output "ami_id" { + value = module.amis.ami_id +} +output "cluster_public_ip" { + value = aws_eip.cluster_eip.*.public_ip +} +output "member_a_public_ip" { + value = aws_eip.member_a_eip.*.public_ip +} +output "member_b_public_ip" { + value = aws_eip.member_b_eip.*.public_ip +} +output "member_a_eni" { + value = aws_network_interface.member_a_external_eni.id +} +output "member_a_ssh" { + value = format("ssh -i %s admin@%s", var.key_name, aws_eip.member_a_eip.public_ip) +} +output "member_b_ssh" { + value = format("ssh -i %s admin@%s", var.key_name, aws_eip.member_b_eip.public_ip) +} +output "member_a_url" { + value = format("https://%s", aws_eip.member_a_eip.public_ip) +} +output "member_b_url" { + value = format("https://%s", aws_eip.member_b_eip.public_ip) +} +output "member_b_eni" { + value = aws_network_interface.member_b_external_eni.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/terraform.tfvars b/deprecated/terraform/aws/R81/cross-az-cluster/terraform.tfvars new file mode 100755 index 00000000..8c6aff9b --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/terraform.tfvars @@ -0,0 +1,42 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_ids = ["subnet-abc123", "subnet-def456"] +private_subnet_ids = ["subnet-abc234", "subnet-def567"] +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/variables.tf b/deprecated/terraform/aws/R81/cross-az-cluster/variables.tf new file mode 100755 index 00000000..c2d66839 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/variables.tf @@ -0,0 +1,181 @@ +// Module: Check Point CloudGuard Network Security Cross AZ Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. At least 2" +} +variable "private_subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. At least 2" +} +variable "private_route_table" { + type = string + description = "(Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R81/cross-az-cluster/versions.tf b/deprecated/terraform/aws/R81/cross-az-cluster/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/cross-az-cluster/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/gateway-master/README.md b/deprecated/terraform/aws/R81/gateway-master/README.md new file mode 100755 index 00000000..c3f4952d --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway-master/README.md @@ -0,0 +1,217 @@ +# Check Point CloudGuard Network Security Gateway Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation + + +See the [Automatically Provision a CloudGuard Security Gateway in AWS](https://supportcenter.us.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk131434) for additional information + +This solution uses the following modules: +- /terraform/aws/gateway +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/gateway-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/gateway: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/gateway: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + + +## Usage +- Fill all variables in the /terraform/aws/gateway-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/gateway-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + } + private_subnets_map = { + "us-east-1a" = 2 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Gateway-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + // --- Quick connect to Smart-1 Cloud (Recommended) --- + gateway_TokenKey = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + + // --- (Optional) Automatic Provisioning with Security Management Server Settings --- + control_gateway_over_public_or_private_address = "private" + management_server = "" + configuration_template = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Gateway instance: + ``` + allocate_and_associate_eip = true + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instance | string | n/a | Check-Point-Gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Security Gateway EC2 Instance | map(string) | n/a | {} | no | +| gateway_version | Gateway version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_TokenKey | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| gateway_hostname | (Optional) Security Gateway prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| control_gateway_over_public_or_private_address | Determines if the Security Gateway is provisioned using its private or public address | string | - public
- private | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | "" | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | "" | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + +## Outputs +| Name | Description | +|------------------------------|----------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| internal_rt_id | The internal route table id | +| vpc_public_subnets_ids_list | A list of the public subnets ids | +| vpc_private_subnets_ids_list | A list of the private subnets ids | +| ami_id | The ami id of the deployed Security Gateway | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group id name | +| gateway_url | URL to the portal of the deployed Security Gateway | +| gateway_public_ip | The deployed Security Gateway Server AWS public ip | +| gateway_instance_id | The deployed Security Gateway AWS instance id | +| gateway_instance_name | The deployed Security Gateway AWS instance name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Gateway Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway-master/locals.tf b/deprecated/terraform/aws/R81/gateway-master/locals.tf new file mode 100755 index 00000000..0ca4134f --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway-master/locals.tf @@ -0,0 +1,48 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters." + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SICKey] must be at least 8 alphanumeric characters" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway-master/main.tf b/deprecated/terraform/aws/R81/gateway-master/main.tf new file mode 100755 index 00000000..dd09ebb4 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway-master/main.tf @@ -0,0 +1,66 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} + +module "launch_gateway_into_vpc" { + source = "../gateway" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_id = module.launch_vpc.public_subnets_ids_list[0] + private_subnet_id = module.launch_vpc.private_subnets_ids_list[0] + private_route_table = aws_route_table.private_subnet_rtb.id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_TokenKey = var.gateway_TokenKey + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + control_gateway_over_public_or_private_address = var.control_gateway_over_public_or_private_address + management_server = var.management_server + configuration_template = var.configuration_template +} diff --git a/deprecated/terraform/aws/R81/gateway-master/output.tf b/deprecated/terraform/aws/R81/gateway-master/output.tf new file mode 100755 index 00000000..2d8a716c --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway-master/output.tf @@ -0,0 +1,33 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "internal_rtb_id" { + value = aws_route_table.private_subnet_rtb.id +} +output "vpc_public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "vpc_private_subnets_ids_list" { + value = module.launch_vpc.private_subnets_ids_list +} +output "ami_id" { + value = module.launch_gateway_into_vpc.ami_id +} +output "permissive_sg_id" { + value = module.launch_gateway_into_vpc.permissive_sg_id +} +output "permissive_sg_name" { + value = module.launch_gateway_into_vpc.permissive_sg_name +} +output "gateway_url" { + value = module.launch_gateway_into_vpc.gateway_url +} +output "gateway_public_ip" { + value = module.launch_gateway_into_vpc.gateway_public_ip +} +output "gateway_instance_id" { + value = module.launch_gateway_into_vpc.gateway_instance_id +} +output "gateway_instance_name" { + value = module.launch_gateway_into_vpc.gateway_instance_name +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway-master/terraform.tfvars b/deprecated/terraform/aws/R81/gateway-master/terraform.tfvars new file mode 100755 index 00000000..a8eb1d58 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway-master/terraform.tfvars @@ -0,0 +1,50 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 +} +private_subnets_map = { + "us-east-1a" = 2 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" + +// --- (Optional) Automatic Provisioning with Security Management Server Settings --- +control_gateway_over_public_or_private_address = "private" +management_server = "" +configuration_template = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway-master/variables.tf b/deprecated/terraform/aws/R81/gateway-master/variables.tf new file mode 100755 index 00000000..1c00c4f3 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway-master/variables.tf @@ -0,0 +1,195 @@ +// Module: Check Point CloudGuard Network Security Gateway into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20." +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instance" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateway" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) Security Gateway prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} + +// --- (Optional) Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the Security Gateway is provisioned using its private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway-master/versions.tf b/deprecated/terraform/aws/R81/gateway-master/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/gateway/README.md b/deprecated/terraform/aws/R81/gateway/README.md new file mode 100755 index 00000000..c9052114 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway/README.md @@ -0,0 +1,192 @@ +# Check Point CloudGuard Network Security Gateway Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation + +See the [Automatically Provision a CloudGuard Security Gateway in AWS](https://supportcenter.us.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk131434) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/gateway/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gateway/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/gateway/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_id = "subnet-123456" + private_subnet_id = "subnet-345678" + private_route_table = "rtb-12345678" + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Gateway-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + gateway_TokenKey = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + + // --- Automatic Provisioning with Security Management Server Settings (optional) --- + control_gateway_over_public_or_private_address = "private" + management_server = "" + configuration_template = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Gateway instance: + ``` + allocate_and_associate_eip = true + ``` + - To create route from '0.0.0.0/0' to the Security Gateway instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the security gateway | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the security gateway | string | n/a | n/a | yes | +| private_route_table | Sets '0.0.0.0/0' route to the Gateway instance in the specified route table (e.g. rtb-12a34567) | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instance | string | n/a | Check-Point-Gateway-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Security Gateway EC2 Instance | map(string) | n/a | {} | no | +| gateway_version | Gateway version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_TokenKey | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| gateway_hostname | (Optional) Security Gateway prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| control_gateway_over_public_or_private_address | Determines if the Security Gateway is provisioned using its private or public address | string | - public
- private | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | "" | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | "" | no | +| gateway_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|-----------------------|----------------------------------------------------| +| ami_id | The ami id of the deployed Security Gateway | +| permissive_sg_id | The permissive security group id | +| permissive_sg_name | The permissive security group id name | +| gateway_url | URL to the portal of the deployed Security Gateway | +| gateway_public_ip | The deployed Security Gateway Server AWS public ip | +| gateway_instance_id | The deployed Security Gateway AWS instance id | +| gateway_instance_name | The deployed Security Gateway AWS instance name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | Improved deployment experience for gateways and clusters managed by Smart-1 Cloud | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Gateway Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway/locals.tf b/deprecated/terraform/aws/R81/gateway/locals.tf new file mode 100755 index 00000000..79c894db --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway/locals.tf @@ -0,0 +1,48 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + //will fail if decode token should contain https:// and .checkpoint.com/app/maas/api/v1/tenant or empty string + split_token = split(" ", var.gateway_TokenKey) + token_decode = base64decode(element(local.split_token, length(local.split_token)-1)) + regex_token_valid = "(^https://(.+).checkpoint.com/app/maas/api/v1/tenant(.+)|^$)" + regex_token = regex(local.regex_token_valid, local.token_decode) == local.token_decode ? 0 : "Smart-1 Cloud token is invalid format" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway/main.tf b/deprecated/terraform/aws/R81/gateway/main.tf new file mode 100755 index 00000000..164d6bf0 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway/main.tf @@ -0,0 +1,119 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.gateway_version + chkp_type = "gateway" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.gateway_name +} + +resource "aws_iam_instance_profile" "gateway_instance_profile" { + count = local.enable_cloudwatch_policy + path = "/" + role = aws_iam_role.gateway_iam_role[count.index].name +} + +resource "aws_iam_role" "gateway_iam_role" { + count = local.enable_cloudwatch_policy + assume_role_policy = data.aws_iam_policy_document.gateway_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "gateway_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + } +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_role.gateway_iam_role[count.index].name + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name +} + +resource "aws_network_interface" "public_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth0" + source_dest_check = false + tags = { + Name = format("%s-external-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} +resource "aws_network_interface" "private_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth1" + source_dest_check = false + tags = { + Name = format("%s-internal-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) } +} + +module "common_eip" { + source = "../modules/common/elastic_ip" + depends_on = [ + module.common_gateway_instance + ] + + allocate_and_associate_eip = var.allocate_and_associate_eip + external_eni_id = aws_network_interface.public_eni.id + private_ip_address = aws_network_interface.public_eni.private_ip +} + +module "common_internal_default_route" { + source = "../modules/common/internal_default_route" + + private_route_table = var.private_route_table + internal_eni_id = aws_network_interface.private_eni.id +} + +module "common_gateway_instance" { + source = "../modules/common/gateway_instance" + + external_eni_id = aws_network_interface.public_eni.id + internal_eni_id = aws_network_interface.private_eni.id + gateway_name = var.gateway_name + management_server = var.management_server + configuration_template = var.configuration_template + control_gateway_over_public_or_private_address = var.control_gateway_over_public_or_private_address + volume_size = var.volume_size + volume_encryption = var.volume_encryption + gateway_version = module.amis.version_license_with_suffix + gateway_instance_type = var.gateway_instance_type + instance_tags = var.instance_tags + key_name = var.key_name + iam_instance_profile_id = (local.enable_cloudwatch_policy == 1 ? aws_iam_instance_profile.gateway_instance_profile[0].id : "") + ami_id = module.amis.ami_id + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_TokenKey = var.gateway_TokenKey + gateway_bootstrap_script = var.gateway_bootstrap_script + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway/output.tf b/deprecated/terraform/aws/R81/gateway/output.tf new file mode 100755 index 00000000..ab3c934f --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway/output.tf @@ -0,0 +1,21 @@ +output "ami_id" { + value = module.amis.ami_id +} +output "permissive_sg_id" { + value = module.common_permissive_sg.permissive_sg_id +} +output "permissive_sg_name" { + value = module.common_permissive_sg.permissive_sg_name +} +output "gateway_url" { + value = format("https://%s", module.common_eip.gateway_eip_public_ip[0]) +} +output "gateway_public_ip" { + value = module.common_eip.gateway_eip_public_ip +} +output "gateway_instance_id" { + value = module.common_gateway_instance.gateway_instance_id +} +output "gateway_instance_name" { + value = module.common_gateway_instance.gateway_instance_name +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway/terraform.tfvars b/deprecated/terraform/aws/R81/gateway/terraform.tfvars new file mode 100755 index 00000000..02b1f781 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway/terraform.tfvars @@ -0,0 +1,46 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_id = "subnet-123456" +private_subnet_id = "subnet-345678" +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Gateway-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +gateway_TokenKey = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" + +// --- Automatic Provisioning with Security Management Server Settings (optional) --- +control_gateway_over_public_or_private_address = "private" +management_server = "" +configuration_template = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway/variables.tf b/deprecated/terraform/aws/R81/gateway/variables.tf new file mode 100755 index 00000000..7d32ab1a --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway/variables.tf @@ -0,0 +1,192 @@ +// Module: Check Point CloudGuard Network Security Gateway into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_id" { + type = string + description = "The public subnet of the security gateway" +} +variable "private_subnet_id" { + type = string + description = "The private subnet of the security gateway" +} +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Security Gateway instance in the specified route table (e.g. rtb-12a34567)" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instance" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateway" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Security Gateway EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) Security Gateway prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} + +// --- (Optional) Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the Security Gateway is provisioned using its private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gateway/versions.tf b/deprecated/terraform/aws/R81/gateway/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/gateway/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/gwlb-master/README.md b/deprecated/terraform/aws/R81/gwlb-master/README.md new file mode 100755 index 00000000..61bfad54 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb-master/README.md @@ -0,0 +1,236 @@ +# Check Point CloudGuard Network Gateway Load Balancer Master Terraform module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [VPC](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/vpc) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` + - Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + + // --- Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + subnets_bit_length = 8 + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb1" + target_group_name = "tg1" + connection_acceptance_required = "false" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "" + gateways_addresses = "" + + // --- Other parameters --- + volume_type = "gp3" + + + ``` + +- Conditional creation + - To enable cloudwatch for gwlb-master: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-configuration | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb1 | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1 | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | Check-Point-GW-tf | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG | R81.20-BYOL | no | +| management_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | Change default shell for the admin user to /etc/cli.sh | +| 20221215 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point CloudGuard Network Gateway Load Balancer master module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/gwlb-master/locals.tf b/deprecated/terraform/aws/R81/gwlb-master/locals.tf new file mode 100755 index 00000000..29a557ee --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb-master/locals.tf @@ -0,0 +1,61 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) + +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gwlb-master/main.tf b/deprecated/terraform/aws/R81/gwlb-master/main.tf new file mode 100755 index 00000000..da8bf39c --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb-master/main.tf @@ -0,0 +1,69 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = {} + subnets_bit_length = var.subnets_bit_length +} + +module "gwlb" { + source = "../gwlb" + providers = { + aws = aws + } + vpc_id = module.launch_vpc.vpc_id + subnet_ids = module.launch_vpc.public_subnets_ids_list + + // --- General Settings --- + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + volume_size = var.volume_size + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + management_server = var.management_server + configuration_template = var.configuration_template + admin_shell = var.admin_shell + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = var.gateway_load_balancer_name + target_group_name = var.target_group_name + connection_acceptance_required = false + enable_cross_zone_load_balancing = var.enable_cross_zone_load_balancing + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateway_management = var.gateway_management + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + + volume_type = var.volume_type +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gwlb-master/output.tf b/deprecated/terraform/aws/R81/gwlb-master/output.tf new file mode 100755 index 00000000..15cb48a3 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb-master/output.tf @@ -0,0 +1,24 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "management_public_ip" { + depends_on = [module.gwlb] + value = module.gwlb[*].management_public_ip +} +output "gwlb_arn" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_arn +} +output "gwlb_service_name" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_service_name +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gwlb-master/terraform.tfvars b/deprecated/terraform/aws/R81/gwlb-master/terraform.tfvars new file mode 100755 index 00000000..f0f13c92 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb-master/terraform.tfvars @@ -0,0 +1,56 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +subnets_bit_length = 8 + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +connection_acceptance_required = "false" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R81/gwlb-master/variables.tf b/deprecated/terraform/aws/R81/gwlb-master/variables.tf new file mode 100755 index 00000000..fd72c46c --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb-master/variables.tf @@ -0,0 +1,274 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "number_of_AZs" { + type = number + description = "Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter" + default = 2 +} +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "connection_acceptance_required" { + type = bool + description = "Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required)." + default = false +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Other parameters --- +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gwlb-master/versions.tf b/deprecated/terraform/aws/R81/gwlb-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/gwlb/README.md b/deprecated/terraform/aws/R81/gwlb/README.md new file mode 100755 index 00000000..de0e043e --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb/README.md @@ -0,0 +1,229 @@ +# Check Point CloudGuard Network Gateway Load Balancer Terraform module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345" + subnet_ids = ["subnet-123457", "subnet-123456"] + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb1" + target_group_name = "tg1" + connection_acceptance_required = "false" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "" + gateways_addresses = "" + + // --- Other parameters --- + volume_type = "gp3" + + + ``` + +- Conditional creation + - To enable cloudwatch for GWLB: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| subnet_ids | The VPC subnets ID | string | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-configuration | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb1 | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1 | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | Check-Point-GW-tf | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231022 | Fixed template to populate x-chkp-tags correctly | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | Change default shell for the admin user to /etc/cli.sh | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220523 | Add support for cross zone load balancing | +| 20220414 | First release of Check Point CloudGuard Network Gateway Load Balancer module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/gwlb/locals.tf b/deprecated/terraform/aws/R81/gwlb/locals.tf new file mode 100755 index 00000000..44363311 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb/locals.tf @@ -0,0 +1,55 @@ +locals { + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gwlb/main.tf b/deprecated/terraform/aws/R81/gwlb/main.tf new file mode 100755 index 00000000..7c4e4616 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb/main.tf @@ -0,0 +1,99 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +module "gateway_load_balancer" { + source = "../modules/common/load_balancer" + + load_balancers_type = "gateway" + instances_subnets = var.subnet_ids + prefix_name = var.gateway_load_balancer_name + internal = true + + security_groups = [] + tags = { + x-chkp-management = var.management_server + x-chkp-template = var.configuration_template + } + vpc_id = var.vpc_id + load_balancer_protocol = "GENEVE" + target_group_port = 6081 + listener_port = 6081 + cross_zone_load_balancing = var.enable_cross_zone_load_balancing +} + +resource "aws_vpc_endpoint_service" "gwlb_endpoint_service" { +depends_on = [module.gateway_load_balancer] + gateway_load_balancer_arns = module.gateway_load_balancer[*].load_balancer_arn + acceptance_required = var.connection_acceptance_required + + tags = { + "Name" = "gwlb-endpoint-service-${var.gateway_load_balancer_name}" + } +} + +module "autoscale_gwlb" { + source = "../autoscale-gwlb" + providers = { + aws = aws + } + depends_on = [module.gateway_load_balancer] + + target_groups = module.gateway_load_balancer[*].target_group_arn + vpc_id = var.vpc_id + subnet_ids = var.subnet_ids + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + metadata_imdsv2_required = var.metadata_imdsv2_required + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + admin_shell = var.admin_shell + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + management_server = var.management_server + configuration_template = var.configuration_template + volume_type = var.volume_type +} + +data "aws_region" "current"{} + +module "management" { + providers = { + aws = aws + } + count = local.deploy_management_condition ? 1 : 0 + source = "../management" + + vpc_id = var.vpc_id + subnet_id = var.subnet_ids[0] + management_name = var.management_server + management_instance_type = var.management_instance_type + key_name = var.key_name + allocate_and_associate_eip = true + volume_encryption = var.enable_volume_encryption ? "alias/aws/ebs" : "" + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + allow_upload_download = var.allow_upload_download + admin_cidr = var.admin_cidr + admin_shell = var.admin_shell + gateway_addresses = var.gateways_addresses + gateway_management = var.gateway_management + management_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"management_gwlb\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; autoprov_cfg -f init AWS -mn ${var.management_server} -tn ${var.configuration_template} -cn gwlb-controller -po ${var.gateways_policy} -otp ${var.gateway_SICKey} -r ${data.aws_region.current.name} -ver ${split("-", var.gateway_version)[0]} -iam; echo -e '\nFinished Bootstrap script\n'" + volume_type = var.volume_type + is_gwlb_iam = true +} diff --git a/deprecated/terraform/aws/R81/gwlb/output.tf b/deprecated/terraform/aws/R81/gwlb/output.tf new file mode 100755 index 00000000..3beba7ee --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb/output.tf @@ -0,0 +1,22 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "gwlb_arn" { + value = module.gateway_load_balancer.load_balancer_arn +} +output "gwlb_service_name" { + value = "com.amazonaws.vpce.${data.aws_region.current.name}.${aws_vpc_endpoint_service.gwlb_endpoint_service.id}" +} +output "management_public_ip" { + depends_on = [module.management] + value = module.management[*].management_public_ip +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gwlb/terraform.tfvars b/deprecated/terraform/aws/R81/gwlb/terraform.tfvars new file mode 100755 index 00000000..0e26ad11 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb/terraform.tfvars @@ -0,0 +1,52 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_ids = ["subnet-123456", "subnet-345678"] + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +connection_acceptance_required = "false" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R81/gwlb/variables.tf b/deprecated/terraform/aws/R81/gwlb/variables.tf new file mode 100755 index 00000000..5f099c6c --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb/variables.tf @@ -0,0 +1,263 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_ids" { + type = list(string) + description = "List of public subnet IDs to launch resources into. Recommended at least 2" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "connection_acceptance_required" { + type = bool + description = "Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required)." + default = false +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Other parameters --- +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/gwlb/versions.tf b/deprecated/terraform/aws/R81/gwlb/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/gwlb/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/management/README.md b/deprecated/terraform/aws/R81/management/README.md new file mode 100755 index 00000000..6d2dc8a6 --- /dev/null +++ b/deprecated/terraform/aws/R81/management/README.md @@ -0,0 +1,201 @@ +# Check Point CloudGuard Network Security Management Server Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Management Server into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Security Management Server with CloudGuard for AWS](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk130372) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/management/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/management/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/management/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_id = "subnet-abc123" + + // --- EC2 Instances Configuration --- + management_name = "CP-Management-tf" + management_instance_type = "m5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- IAM Permissions --- + iam_permissions = "Create with read permissions" + predefined_role = "" + sts_roles = [] + + // --- Check Point Settings --- + management_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + // --- Security Management Server Settings --- + management_hostname = "mgmt-tf" + management_installation_type = "Primary management" + SICKey = "" + allow_upload_download = "true" + gateway_management = "Locally managed" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + primary_ntp = "" + secondary_ntp = "" + management_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Management instance: + ``` + allocate_and_associate_eip = true + ``` + - To create IAM Role: + ``` + iam_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_id | To access the instance from the internet, make sure the subnet has a route to the internet | string | n/a | n/a | yes | +| management_name | (Optional) The name tag of the Security Management instance | string | n/a | Check-Point-Management-tf | no | +| management_instance_type | The instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Management EC2 Instance | map(string) | n/a | {} | no | +| iam_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| predefined_role | (Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing' | string | n/a | "" | no | +| sts_roles | (Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing' | list(string) | n/a | [] | no | +| management_version | Management version and license | string | - R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| management_password_hash | (Optional) Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) | string | n/a | "" | no | +| management_hostname | (Optional) Security Management Server prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| management_installation_type | Determines if this is the primary management server, secondary management server or log server | string | - Primary management
- Secondary management
- Log Server
| Primary management | yes | +| SICKey | Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Security Management Server | string | valid CIDR | 0.0.0.0/0 | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| management_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|--------------------------------------------------------------| +| management_instance_id | The deployed Security Management Server AWS instance id | +| management_instance_name | The deployed Security Management AWS instance name | +| management_instance_tags | The deployed Security Management Server AWS tags | +| management_public_ip | The deployed Security Management Server AWS public ip | +| management_url | URL to the portal of the deployed Security Management Server | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240207 | Added Log Server installation support | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Security Management Server Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/management/locals.tf b/deprecated/terraform/aws/R81/management/locals.tf new file mode 100755 index 00000000..896719ba --- /dev/null +++ b/deprecated/terraform/aws/R81/management/locals.tf @@ -0,0 +1,76 @@ +locals { + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.iam_permissions) + + use_role = var.iam_permissions == "None (configure later)" ? 0 : 1 + create_iam_role = var.iam_permissions == "Create with assume role permissions (specify an STS role ARN)" || var.iam_permissions == "Create with read permissions" || var.iam_permissions == "Create with read-write permissions" + pre_role = (local.use_role == 1 && local.create_iam_role == false) ? 1 : 0 + new_instance_profile = (local.create_iam_role == true && local.use_role == 1) ? 1 : 0 + + new_instance_profile_general = local.new_instance_profile == 1 && var.is_gwlb_iam == false ? 1 : 0 + new_instance_profile_gwlb = local.new_instance_profile == 1 && var.is_gwlb_iam ? 1 : 0 + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // Will fail if var.gateway_management is invalid + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + regex_valid_sic_key = "(|[a-zA-Z0-9]{8,})" + // Will fail if var.SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.SICKey) == var.SICKey ? 0 : "Variable [SICKey] must be at least 8 alphanumeric characters" + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.management_version), 0) + + management_bootstrap_script64 = base64encode(var.management_bootstrap_script) + management_SICkey_base64=base64encode(var.SICKey) + management_password_hash_base64=base64encode(var.management_password_hash) + maintenance_mode_password_hash_base64=base64encode(var.management_maintenance_mode_password_hash) + + manage_over_the_internet = var.gateway_management == "Over the internet" ? true : false + manage_over_internet_and_EIP = var.allocate_and_associate_eip && local.manage_over_the_internet ? true : false + pub_mgmt = local.manage_over_internet_and_EIP ? true : false + + management_installation_type_allowed_values = [ + "Primary management", + "Secondary management", + "Log Server"] + validate_management_installation_type = index(local.management_installation_type_allowed_values, var.management_installation_type) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/management/main.tf b/deprecated/terraform/aws/R81/management/main.tf new file mode 100755 index 00000000..3714dfa2 --- /dev/null +++ b/deprecated/terraform/aws/R81/management/main.tf @@ -0,0 +1,221 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.management_version + chkp_type = "management" +} + +resource "aws_security_group" "management_sg" { + description = "terraform Management security group" + vpc_id = var.vpc_id + name_prefix = format("%s_SecurityGroup", var.management_name) + // Group name + tags = { + Name = format("%s_SecurityGroup", var.management_name) + // Resource name + } + ingress { + from_port = 257 + to_port = 257 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18191 + to_port = 18191 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18192 + to_port = 18192 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18208 + to_port = 18208 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18210 + to_port = 18210 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18211 + to_port = 18211 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18221 + to_port = 18221 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18264 + to_port = 18264 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + + ingress { + from_port = 22 + to_port = 22 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 443 + to_port = 443 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 18190 + to_port = 18190 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 19009 + to_port = 19009 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } +} + +resource "aws_network_interface" "external-eni" { + subnet_id = var.subnet_id + security_groups = [aws_security_group.management_sg.id] + description = "eth0" + source_dest_check = true + tags = { + Name = format("%s-network_interface", var.management_name) + } +} + +resource "aws_eip" "eip" { + count = var.allocate_and_associate_eip ? 1 : 0 + network_interface = aws_network_interface.external-eni.id +} + +resource "aws_iam_instance_profile" "management_instance_profile" { + count = local.pre_role + path = "/" + role = var.predefined_role +} + +resource "aws_launch_template" "management_launch_template" { + depends_on = [ + aws_network_interface.external-eni, + aws_eip.eip + ] + + instance_type = var.management_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = local.use_role == 1 ? (local.pre_role == 1 ? aws_iam_instance_profile.management_instance_profile[0].id : join("", (var.is_gwlb_iam == true ? module.cme_iam_role_gwlb.*.cme_iam_profile_name : module.cme_iam_role.*.cme_iam_profile_name))): "" + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.external-eni.id + device_index = 0 + } +} + +resource "aws_instance" "management-instance" { + depends_on = [ + aws_launch_template.management_launch_template + ] + + launch_template { + id = aws_launch_template.management_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.management_name + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = var.volume_type + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + lifecycle { + ignore_changes = [ebs_block_device,] + } + + user_data = templatefile("${path.module}/management_userdata.yaml", { + // script's arguments + Hostname = var.management_hostname, + PasswordHash = local.management_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + NTPPrimary = var.primary_ntp + NTPSecondary = var.secondary_ntp + Shell = var.admin_shell, + AdminSubnet = var.admin_cidr + ManagementInstallationType = var.management_installation_type + SICKey = local.management_SICkey_base64, + OsVersion = local.version_split + EnableInstanceConnect = var.enable_instance_connect + AllocateElasticIP = var.allocate_and_associate_eip + GatewayManagement = var.gateway_management + BootstrapScript = local.management_bootstrap_script64 + PubMgmt = local.pub_mgmt + + }) +} + +module "cme_iam_role" { + source = "../cme-iam-role" + providers = { + aws = aws + } + count = local.new_instance_profile_general + + sts_roles = var.sts_roles + permissions = var.iam_permissions +} + +module "cme_iam_role_gwlb" { + source = "../cme-iam-role-gwlb" + providers = { + aws = aws + } + count = local.new_instance_profile_gwlb + + sts_roles = var.sts_roles + permissions = var.iam_permissions +} diff --git a/deprecated/terraform/aws/R81/management/management_userdata.yaml b/deprecated/terraform/aws/R81/management/management_userdata.yaml new file mode 100755 index 00000000..cfd9e5dc --- /dev/null +++ b/deprecated/terraform/aws/R81/management/management_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py sicKey=\"${SICKey}\" installationType=\"management\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20240704\" templateName=\"management\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" "management_installation_type=\"${ManagementInstallationType}\"" adminSubnet=\"${AdminSubnet}\" allocatePublicAddress=\"${AllocateElasticIP}\" overTheInternet=\"${PubMgmt}\" bootstrapScript64=\"${BootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/management/output.tf b/deprecated/terraform/aws/R81/management/output.tf new file mode 100755 index 00000000..da20727b --- /dev/null +++ b/deprecated/terraform/aws/R81/management/output.tf @@ -0,0 +1,19 @@ +output "Deployment" { + value = "Finalizing configuration may take up to 20 minutes after deployment is finished." +} + +output "management_instance_id" { + value = aws_instance.management-instance.id +} +output "management_instance_name" { + value = aws_instance.management-instance.tags["Name"] +} +output "management_instance_tags" { + value = aws_instance.management-instance.tags +} +output "management_public_ip" { + value = aws_instance.management-instance.public_ip +} +output "management_url" { + value = format("https://%s", aws_instance.management-instance.public_ip) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/management/terraform.tfvars b/deprecated/terraform/aws/R81/management/terraform.tfvars new file mode 100755 index 00000000..81891681 --- /dev/null +++ b/deprecated/terraform/aws/R81/management/terraform.tfvars @@ -0,0 +1,42 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_id = "subnet-abc123" + +// --- EC2 Instances Configuration --- +management_name = "CP-Management-tf" +management_instance_type = "m5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- IAM Permissions --- +iam_permissions = "Create with read permissions" +predefined_role = "" +sts_roles = [] + +// --- Check Point Settings --- +management_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +// --- Security Management Server Settings --- +management_hostname = "mgmt-tf" +management_installation_type = "Primary management" +SICKey = "" +allow_upload_download = "true" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "" +secondary_ntp = "" +management_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" diff --git a/deprecated/terraform/aws/R81/management/variables.tf b/deprecated/terraform/aws/R81/management/variables.tf new file mode 100755 index 00000000..763918f0 --- /dev/null +++ b/deprecated/terraform/aws/R81/management/variables.tf @@ -0,0 +1,194 @@ +// Module: Check Point CloudGuard Network Security Management Server into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_id" { + type = string + description = "To access the instance from the internet, make sure the subnet has a route to the internet" +} + +// --- EC2 Instance Configuration --- +variable "management_name" { + type = string + description = "(Optional) The name tag of the Security Management instance" + default = "Check-Point-Management-tf" +} +variable "management_instance_type" { + type = string + description = "The instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable AWS Instance Connect - Ec2 Instance Connect is not supported with versions prior to R80.40" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Management EC2 Instance" + default = {} +} + +// --- IAM Permissions (ignored when the installation is not Primary Management Server) --- +variable "iam_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read permissions" +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing'" + default = "" +} +variable "sts_roles" { + type = list(string) + description = "(Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing'" + default = [] +} + +// --- Check Point Settings --- +variable "management_version" { + type = string + description = "Management version and license" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Security Management Server Settings --- +variable "management_hostname" { + type = string + description = "(Optional) Security Management Server prompt hostname" + default = "" +} +variable "management_installation_type" { + type = string + description = "Determines the Management Server installation type: Primary management, Secondary management, Log Server" + default = "Primary management" +} +variable "SICKey" { + type = string + description = "Mandatory only when deploying a secondary Management Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Security Management Server" + default = "0.0.0.0/0" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "management_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "is_gwlb_iam" { + type = bool + default = false +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/management/versions.tf b/deprecated/terraform/aws/R81/management/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/management/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/mds/README.md b/deprecated/terraform/aws/R81/mds/README.md new file mode 100755 index 00000000..518acc19 --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/README.md @@ -0,0 +1,191 @@ +# Check Point CloudGuard Network Multi-Domain Server Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Multi-Domain Server into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Multi-Domain Management Deployment on AWS](https://supportcenter.us.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk143213) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/mds/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/mds/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/mds/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + subnet_id = "subnet-abc123" + + // --- EC2 Instances Configuration --- + mds_name = "CP-MDS-tf" + mds_instance_type = "m5.12xlarge" + key_name = "publickey" + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- IAM Permissions --- + iam_permissions = "Create with read permissions" + predefined_role = "" + sts_roles = [] + + // --- Check Point Settings --- + mds_version = "R81.20-BYOL" + mds_admin_shell = "/etc/cli.sh" + mds_password_hash = "" + mds_maintenance_mode_password_hash = "" + + // --- Multi-Domain Server Settings --- + mds_hostname = "mds-tf" + mds_SICKey = "" + allow_upload_download = "true" + mds_installation_type = "Primary Multi-Domain Server" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + primary_ntp = "" + secondary_ntp = "" + mds_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + ``` + +- Conditional creation + - To create IAM Role: + ``` + iam_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + and + mds_installation_type = "Primary Multi-Domain Server" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| subnet_id | To access the instance from the internet, make sure the subnet has a route to the internet | string | n/a | n/a | yes | +| mds_name | (Optional) The name tag of the Multi-Domain Server instance | string | n/a | Check-Point-MDS-tf | no | +| mds_instance_type | The instance type of the Multi-Domain Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.12xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Multi-Domain Server EC2 Instance | map(string) | n/a | {} | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| iam_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read permissions | no | +| predefined_role | (Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing' | string | n/a | "" | no | +| sts_roles | (Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing' | list(string) | n/a | [] | no | +| mds_version | Multi-Domain Server version and license | string | - R81-BYOL
- R81.10-BYOL
- R81.20-BYOL
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| mds_admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| mds_password_hash | (Optional) Admin user's password hash (use command "openssl passwd -6 PASSWORD" to get the PASSWORD's hash) | string | n/a | "" | no | +| mds_hostname | (Optional) Multi-Domain Server prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| mds_SICKey | Mandatory if deploying a Secondary Multi-Domain Server or Multi-Domain Log Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| mds_installation_type | Determines the Multi-Domain Server installation type | string | - Primary Multi-Domain Server
- Secondary Multi-Domain Server
- Multi-Domain Log Server | Primary Multi-Domain Server | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Multi-Domain Server | string | valid CIDR | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Multi-Domain Server | string | valid CIDR | 0.0.0.0/0 | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| mds_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| mds_maintenance_mode_password_hash | (optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here). | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|-------------------|----------------------------------------------------| +| mds_instance_id | The deployed Multi-Domain Server AWS instance id | +| mds_instance_name | The deployed Multi-Domain Server AWS instance name | +| mds_instance_tags | The deployed Multi-Domain Server AWS tags | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Multi-Domain Server Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/mds/locals.tf b/deprecated/terraform/aws/R81/mds/locals.tf new file mode 100755 index 00000000..7dd690a2 --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/locals.tf @@ -0,0 +1,69 @@ +locals { + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.iam_permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.iam_permissions) + + installation_type_allowed_values = [ + "Primary Multi-Domain Server", + "Secondary Multi-Domain Server", + "Multi-Domain Log Server"] + // Will fail if var.mds_installation_type is invalid + validate_installation_type = index(local.installation_type_allowed_values, var.mds_installation_type) + + primary_mds = var.mds_installation_type == "Primary Multi-Domain Server" + secondary_mds = var.mds_installation_type == "Secondary Multi-Domain Server" + + use_role = var.iam_permissions != "None (configure later)" && local.primary_mds ? 1 : 0 + create_iam_role = (local.primary_mds) && (var.iam_permissions == "Create with assume role permissions (specify an STS role ARN)" || var.iam_permissions == "Create with read permissions" || var.iam_permissions == "Create with read-write permissions") + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.mds_admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.mds_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.mds_hostname) == var.mds_hostname ? 0 : "Variable [mds_hostname] must be a valid hostname label or an empty string" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_mds_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.mds_password_hash is invalid + regex_mds_password_hash = regex(local.regex_valid_mds_password_hash, var.mds_password_hash) == var.mds_password_hash ? 0 : "Variable [mds_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_mds_password_hash, var.mds_maintenance_mode_password_hash) == var.mds_maintenance_mode_password_hash ? 0 : "Variable [mds_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_sic_key = "(|[a-zA-Z0-9]{8,})" + // Will fail if var.mds_SICKey is invalid + regex_sic_result = regex(local.regex_valid_sic_key, var.mds_SICKey) == var.mds_SICKey ? 0 : "Variable [mds_SICKey] must be at least 8 alphanumeric characters" + //Splits the version and licence and returns the os version + version_split = element(split("-", var.mds_version), 0) + + mds_bootstrap_script64 = base64encode(var.mds_bootstrap_script) + mds_SICkey_base64 = base64encode(var.mds_SICKey) + mds_password_hash_base64 =base64encode(var.mds_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.mds_maintenance_mode_password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/mds/main.tf b/deprecated/terraform/aws/R81/mds/main.tf new file mode 100755 index 00000000..8a22b264 --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/main.tf @@ -0,0 +1,194 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.mds_version + chkp_type = "mds" +} + +resource "aws_security_group" "mds_sg" { + description = "terraform Multi-Domain Server security group" + vpc_id = var.vpc_id + name_prefix = format("%s_SecurityGroup", var.mds_name) + // Group name + tags = { + Name = format("%s_SecurityGroup", var.mds_name) + // Resource name + } + ingress { + from_port = 257 + to_port = 257 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 8211 + to_port = 8211 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18191 + to_port = 18191 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18192 + to_port = 18192 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18208 + to_port = 18208 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18210 + to_port = 18210 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18211 + to_port = 18211 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18221 + to_port = 18221 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 18264 + to_port = 18264 + protocol = "tcp" + cidr_blocks = [var.gateway_addresses] + } + ingress { + from_port = 22 + to_port = 22 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 443 + to_port = 443 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 18190 + to_port = 18190 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + ingress { + from_port = 19009 + to_port = 19009 + protocol = "tcp" + cidr_blocks = [var.admin_cidr] + } + + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } +} + +resource "aws_iam_instance_profile" "mds_instance_profile" { + count = local.use_role + path = "/" + role = local.create_iam_role ? join("", module.cme_iam_role.*.cme_iam_role_name) : var.predefined_role +} + +resource "aws_network_interface" "external-eni" { + subnet_id = var.subnet_id + security_groups = [aws_security_group.mds_sg.id] + description = "eth0" + source_dest_check = true + tags = { + Name = format("%s-network_interface", var.mds_name) + } +} + +resource "aws_launch_template" "mds_launch_template" { + instance_type = var.mds_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = local.use_role == 1 ? aws_iam_instance_profile.mds_instance_profile[0].id : "" + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.external-eni.id + device_index = 0 + } +} + +resource "aws_instance" "mds-instance" { + launch_template { + id = aws_launch_template.mds_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.mds_name + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + user_data = templatefile("${path.module}/mds_userdata.yaml", { + // script's arguments + Hostname = var.mds_hostname, + PasswordHash = local.mds_password_hash_base64 + MaintenanceModePassword = local.maintenance_mode_password_hash_base64 + AllowUploadDownload = var.allow_upload_download, + NTPPrimary = var.primary_ntp + NTPSecondary = var.secondary_ntp + Shell = var.mds_admin_shell, + AdminSubnet = var.admin_cidr + IsPrimary = local.primary_mds + IsSecondary = local.secondary_mds + SICKey = local.mds_SICkey_base64, + EnableInstanceConnect = var.enable_instance_connect + BootstrapScript = local.mds_bootstrap_script64 + OsVersion = local.version_split + }) +} + +module "cme_iam_role" { + source = "../cme-iam-role" + providers = { + aws = aws + } + count = local.create_iam_role ? 1 : 0 + + sts_roles = var.sts_roles + permissions = var.iam_permissions +} diff --git a/deprecated/terraform/aws/R81/mds/mds_userdata.yaml b/deprecated/terraform/aws/R81/mds/mds_userdata.yaml new file mode 100755 index 00000000..cd0085c6 --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/mds_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py sicKey=\"${SICKey}\" installationType=\"mds\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20240704\" templateName=\"mds\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" primary=\"${IsPrimary}\" secondary=\"${IsSecondary}\" adminSubnet=\"${AdminSubnet}\" bootstrapScript64=\"${BootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/mds/output.tf b/deprecated/terraform/aws/R81/mds/output.tf new file mode 100755 index 00000000..c1d3783a --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/output.tf @@ -0,0 +1,13 @@ +output "Deployment" { + value = "Finalizing configuration may take up to 20 minutes after deployment is finished." +} + +output "mds_instance_id" { + value = aws_instance.mds-instance.id +} +output "mds_instance_name" { + value = aws_instance.mds-instance.tags["Name"] +} +output "mds_instance_tags" { + value = aws_instance.mds-instance.tags +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/mds/terraform.tfvars b/deprecated/terraform/aws/R81/mds/terraform.tfvars new file mode 100755 index 00000000..e79af359 --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/terraform.tfvars @@ -0,0 +1,41 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +subnet_id = "subnet-abc123" + +// --- EC2 Instances Configuration --- +mds_name = "CP-MDS-tf" +mds_instance_type = "m5.12xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- IAM Permissions --- +iam_permissions = "Create with read permissions" +predefined_role = "" +sts_roles = [] + +// --- Check Point Settings --- +mds_version = "R81.20-BYOL" +mds_admin_shell = "/etc/cli.sh" +mds_password_hash = "" +mds_maintenance_mode_password_hash = "" + +// --- Multi-Domain Server Settings --- +mds_hostname = "mds-tf" +mds_SICKey = "" +allow_upload_download = "true" +mds_installation_type = "Primary Multi-Domain Server" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" +primary_ntp = "" +secondary_ntp = "" +mds_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" diff --git a/deprecated/terraform/aws/R81/mds/variables.tf b/deprecated/terraform/aws/R81/mds/variables.tf new file mode 100755 index 00000000..f4218e4c --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/variables.tf @@ -0,0 +1,175 @@ +// Module: Check Point CloudGuard Network Multi-Domain Server into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "subnet_id" { + type = string + description = "To access the instance from the internet, make sure the subnet has a route to the internet" +} + +// --- EC2 Instance Configuration --- +variable "mds_name" { + type = string + description = "(Optional) The name tag of the Multi-Domain Server instance" + default = "Check-Point-MDS-tf" +} +variable "mds_instance_type" { + type = string + description = "The instance type of the Multi-Domain Server" + default = "m5.2xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "mds" + instance_type = var.mds_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Multi-Domain Server EC2 Instance" + default = {} +} + +// --- IAM Permissions (ignored when the installation type is not Primary Multi-Domain Server) --- +variable "iam_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read permissions" +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if var.iam_permissions is not set to 'Use existing'" + default = "" +} +variable "sts_roles" { + type = list(string) + description = "(Optional) The IAM role will be able to assume these STS Roles (list of ARNs). Ignored if var.iam_permissions is set to 'None' or 'Use existing'" + default = [] +} + +// --- Check Point Settings --- +variable "mds_version" { + type = string + description = "Multi-Domain Server version and license" + default = "R81.20-BYOL" +} +module "validate_mds_version" { + source = "../modules/common/version_license" + + chkp_type = "mds" + version_license = var.mds_version +} +variable "mds_admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "mds_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "mds_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Multi-Domain Server Settings --- +variable "mds_hostname" { + type = string + description = "(Optional) Multi-Domain Server prompt hostname" + default = "" +} +variable "mds_SICKey" { + type = string + description = "Mandatory if deploying a Secondary Multi-Domain Server or Multi-Domain Log Server, the Secure Internal Communication key creates trusted connections between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "mds_installation_type" { + type = string + description = "Determines the Multi-Domain Server installation type" + default = "Primary Multi-Domain Server" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Multi-Domain Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Multi-Domain Server" + default = "0.0.0.0/0" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "mds_bootstrap_script" { + type = string + description = "(Optional) Semicolon (;) separated commands to run on the initial boot" + default = "" +} diff --git a/deprecated/terraform/aws/R81/mds/versions.tf b/deprecated/terraform/aws/R81/mds/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/mds/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/modules/amis/main.tf b/deprecated/terraform/aws/R81/modules/amis/main.tf new file mode 100755 index 00000000..b97de4e1 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/amis/main.tf @@ -0,0 +1,23 @@ +locals { + amis_yaml_regionMap = yamldecode(split("Resources", data.http.amis_yaml_http.response_body)[0]).Mappings.RegionMap + amis_yaml_converterMap = yamldecode(split("Resources", data.http.amis_yaml_http.response_body)[0]).Mappings.ConverterMap + + + // Variables example: + // version_license = "R81.10-PAYG-NGTX" + // RESULT: + // version_license_key = "R81.10-PAYG-NGTX-GW" + + // version_license_value = "R8110PAYGNGTXGW" + + version_license_key_mgmt_gw = format("%s%s", var.version_license, var.chkp_type == "gateway" ? "-GW" : var.chkp_type == "management"? "-MGMT" : var.chkp_type == "mds" ? "-MGMT" : "") + version_license_key = var.chkp_type == "standalone" ? format("%s%s", var.version_license, element(split("-", var.version_license), 1) == "BYOL" ? "-MGMT" : "") : local.version_license_key_mgmt_gw + + version_license_value = local.amis_yaml_converterMap[local.version_license_key]["Value"] + + // Variables example: + // region = "us-east-1" + // version_license_key - see above + // RESULT: local.ami_id = "ami-1234567" + ami_id = local.amis_yaml_regionMap[local.region][local.version_license_value] +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/amis/output.tf b/deprecated/terraform/aws/R81/modules/amis/output.tf new file mode 100755 index 00000000..0be16a15 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/amis/output.tf @@ -0,0 +1,6 @@ +output "ami_id" { + value = local.ami_id +} +output "version_license_with_suffix" { + value = local.version_license_key +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/amis/variables.tf b/deprecated/terraform/aws/R81/modules/amis/variables.tf new file mode 100755 index 00000000..3cbf7b1b --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/amis/variables.tf @@ -0,0 +1,26 @@ +variable "amis_url" { + type = string + description = "URL to amis.yaml" + default = "https://cgi-cfts-staging.s3.amazonaws.com/utils/amis.yaml" +} + +data "http" "amis_yaml_http" { + url = var.amis_url +} + +data "aws_region" "current" {} +locals { + region = data.aws_region.current.name +} + +// --- Version & License --- +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +variable "version_license" { + type = string + description = "Version and license" +} + diff --git a/deprecated/terraform/aws/R81/modules/cloudwatch-policy/main.tf b/deprecated/terraform/aws/R81/modules/cloudwatch-policy/main.tf new file mode 100755 index 00000000..3d191a01 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/cloudwatch-policy/main.tf @@ -0,0 +1,18 @@ +data "aws_iam_policy_document" "policy_document" { + version = "2012-10-17" + statement { + actions = ["cloudwatch:PutMetricData"] + effect = "Allow" + resources = ["*"] + } +} + +resource "aws_iam_policy" "policy" { + name_prefix = format("%s-iam_policy", var.tag_name) + policy = data.aws_iam_policy_document.policy_document.json +} + +resource "aws_iam_role_policy_attachment" "attachment" { + role = var.role + policy_arn = aws_iam_policy.policy.arn +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/cloudwatch-policy/variables.tf b/deprecated/terraform/aws/R81/modules/cloudwatch-policy/variables.tf new file mode 100755 index 00000000..2d3f9452 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/cloudwatch-policy/variables.tf @@ -0,0 +1,9 @@ +variable "tag_name" { + type = string + description = "(Optional) IAM policy name prefix" + default = "cloudwatch" +} +variable "role" { + type = string + description = "A IAM role to attach the cloudwatch policy to it" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/cluster-iam-role/main.tf b/deprecated/terraform/aws/R81/modules/cluster-iam-role/main.tf new file mode 100755 index 00000000..b56eacd6 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/cluster-iam-role/main.tf @@ -0,0 +1,38 @@ +resource "aws_iam_role" "cluster_iam_role" { + assume_role_policy = data.aws_iam_policy_document.cluster_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "cluster_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + } +} + +data "aws_iam_policy_document" "cluster_role_policy_doc" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = [ + "ec2:AssignPrivateIpAddresses", + "ec2:AssociateAddress", + "ec2:CreateRoute", + "ec2:DescribeNetworkInterfaces", + "ec2:DescribeRouteTables", + "ec2:ReplaceRoute"] + resources = ["*"] + } +} +resource "aws_iam_policy" "cluster_role_policy" { + policy = data.aws_iam_policy_document.cluster_role_policy_doc.json +} +resource "aws_iam_role_policy_attachment" "attach_policy" { + policy_arn = aws_iam_policy.cluster_role_policy.arn + role = aws_iam_role.cluster_iam_role.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/cluster-iam-role/output.tf b/deprecated/terraform/aws/R81/modules/cluster-iam-role/output.tf new file mode 100755 index 00000000..7bbf0351 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/cluster-iam-role/output.tf @@ -0,0 +1,9 @@ +output "cluster_iam_role" { + value = aws_iam_role.cluster_iam_role +} +output "cluster_iam_role_arn" { + value = aws_iam_role.cluster_iam_role.arn +} +output "cluster_iam_role_name" { + value = aws_iam_role.cluster_iam_role.name +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/elastic_ip/locals.tf b/deprecated/terraform/aws/R81/modules/common/elastic_ip/locals.tf new file mode 100755 index 00000000..c4af5bca --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/elastic_ip/locals.tf @@ -0,0 +1,3 @@ +locals { + allocate_and_associate_eip_condition = var.allocate_and_associate_eip == true ? 1 : 0 +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/elastic_ip/main.tf b/deprecated/terraform/aws/R81/modules/common/elastic_ip/main.tf new file mode 100755 index 00000000..879748a9 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/elastic_ip/main.tf @@ -0,0 +1,10 @@ +resource "aws_eip" "gateway_eip" { + count = local.allocate_and_associate_eip_condition + network_interface = var.external_eni_id +} +resource "aws_eip_association" "address_assoc" { + count = local.allocate_and_associate_eip_condition + allocation_id = aws_eip.gateway_eip[count.index].id + network_interface_id = var.external_eni_id + private_ip_address = var.private_ip_address +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/elastic_ip/output.tf b/deprecated/terraform/aws/R81/modules/common/elastic_ip/output.tf new file mode 100755 index 00000000..31857b83 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/elastic_ip/output.tf @@ -0,0 +1,9 @@ +output "gateway_eip_id" { + value = aws_eip.gateway_eip.*.id +} +output "gateway_eip_public_ip" { + value = aws_eip.gateway_eip.*.public_ip +} +output "gateway_eip_attached_instance" { + value = aws_eip.gateway_eip.*.instance +} diff --git a/deprecated/terraform/aws/R81/modules/common/elastic_ip/variables.tf b/deprecated/terraform/aws/R81/modules/common/elastic_ip/variables.tf new file mode 100755 index 00000000..c6881436 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/elastic_ip/variables.tf @@ -0,0 +1,13 @@ +variable "allocate_and_associate_eip" { + type = bool + description = "If set to TRUE, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "external_eni_id" { + type = string + description = "The external-eni of the security gateway" +} +variable "private_ip_address" { + type = string + description = "The primary or secondary private IP address to associate with the Elastic IP address. " +} diff --git a/deprecated/terraform/aws/R81/modules/common/gateway_instance/gateway_userdata.yaml b/deprecated/terraform/aws/R81/modules/common/gateway_instance/gateway_userdata.yaml new file mode 100755 index 00000000..ba55e025 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/gateway_instance/gateway_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" sicKey=\"${SICKey}\" "smart1CloudToken=\"${TokenKey}\"" installationType=\"gateway\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20240704\" templateName=\"gateway\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" bootstrapScript64=\"${GatewayBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/gateway_instance/locals.tf b/deprecated/terraform/aws/R81/modules/common/gateway_instance/locals.tf new file mode 100755 index 00000000..a0d9034d --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/gateway_instance/locals.tf @@ -0,0 +1,39 @@ +locals { + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [lambda_scheduled_interval] must be a valid hostname label or an empty string" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + volume_encryption_condition = var.volume_encryption != "" ? true : false + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + gateway_SICkey_base64 = base64encode(var.gateway_SICKey) + gateway_password_hash_base64 = base64encode(var.gateway_password_hash) + gateway_maintenance_mode_password_hash_base64 = base64encode(var.gateway_maintenance_mode_password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/gateway_instance/main.tf b/deprecated/terraform/aws/R81/modules/common/gateway_instance/main.tf new file mode 100755 index 00000000..38382cc2 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/gateway_instance/main.tf @@ -0,0 +1,63 @@ +resource "aws_launch_template" "gateway_launch_template" { + key_name = var.key_name + image_id = var.ami_id + instance_type = var.gateway_instance_type + description = "Initial launch template version" + + iam_instance_profile { + name = var.iam_instance_profile_id + } + + network_interfaces { + network_interface_id = var.external_eni_id + device_index = 0 + } + + network_interfaces { + network_interface_id = var.internal_eni_id + device_index = 1 + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } +} + +resource "aws_instance" "gateway_instance" { + launch_template { + id = aws_launch_template.gateway_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.gateway_name + x-chkp-tags = format("management=%s:template=%s:ip-address=%s", var.management_server, var.configuration_template, var.control_gateway_over_public_or_private_address) + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition ? true : false + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + user_data = templatefile("${path.module}/gateway_userdata.yaml", { + // script's arguments + PasswordHash = local.gateway_password_hash_base64, + MaintenanceModePassword = local.gateway_maintenance_mode_password_hash_base64, + Shell = var.admin_shell, + SICKey = local.gateway_SICkey_base64, + TokenKey = var.gateway_TokenKey, + GatewayBootstrapScript = local.gateway_bootstrap_script64, + Hostname = var.gateway_hostname, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + EnableInstanceConnect = var.enable_instance_connect, + OsVersion = local.version_split + }) +} diff --git a/deprecated/terraform/aws/R81/modules/common/gateway_instance/output.tf b/deprecated/terraform/aws/R81/modules/common/gateway_instance/output.tf new file mode 100755 index 00000000..0c5f6d02 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/gateway_instance/output.tf @@ -0,0 +1,9 @@ +output "gateway_instance_id" { + value = aws_instance.gateway_instance.id +} +output "gateway_instance_arn" { + value = aws_instance.gateway_instance.arn +} +output "gateway_instance_name" { + value = aws_instance.gateway_instance.tags["Name"] +} diff --git a/deprecated/terraform/aws/R81/modules/common/gateway_instance/variables.tf b/deprecated/terraform/aws/R81/modules/common/gateway_instance/variables.tf new file mode 100755 index 00000000..0e1a010c --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/gateway_instance/variables.tf @@ -0,0 +1,147 @@ +variable "external_eni_id" { + type = string + description = "The external-eni of the security gateway" +} +variable "internal_eni_id" { + type = string + description = "The internal-eni of the security gateway" +} +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway-tf" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters." + } +} +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the Security Gateway is provisioned using its private or public address" + default = "private" +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')." + default = "alias/aws/ebs" +} +variable "gateway_version" { + type = string + description = "Gateway version & license" + default = "R81.20-BYOL" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instance." + default = {} +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "ami_id" { + type = string + description = "The AMI to use for the instance" +} +variable "iam_instance_profile_id" { + type = string + description = "The IAM instance profile id" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_TokenKey" { + type = string + description = "Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud." +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional)" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "primary_ntp" { + type = string + description = "(Optional)" + default = "" +} +variable "secondary_ntp" { + type = string + description = "(Optional)" + default = "" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/instance_type/main.tf b/deprecated/terraform/aws/R81/modules/common/instance_type/main.tf new file mode 100755 index 00000000..22fffe49 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/instance_type/main.tf @@ -0,0 +1,353 @@ +locals { + gw_types = [ + "c4.large", + "c4.xlarge", + "c5.large", + "c5.xlarge", + "c5.2xlarge", + "c5.4xlarge", + "c5.9xlarge", + "c5.12xlarge", + "c5.18xlarge", + "c5.24xlarge", + "c5n.large", + "c5n.xlarge", + "c5n.2xlarge", + "c5n.4xlarge", + "c5n.9xlarge", + "c5n.18xlarge", + "c5d.large", + "c5d.xlarge", + "c5d.2xlarge", + "c5d.4xlarge", + "c5d.9xlarge", + "c5d.12xlarge", + "c5d.18xlarge", + "c5d.24xlarge", + "m5.large", + "m5.xlarge", + "m5.2xlarge", + "m5.4xlarge", + "m5.8xlarge", + "m5.12xlarge", + "m5.16xlarge", + "m5.24xlarge", + "m6i.large", + "m6i.xlarge", + "m6i.2xlarge", + "m6i.4xlarge", + "m6i.8xlarge", + "m6i.12xlarge", + "m6i.16xlarge", + "m6i.24xlarge", + "m6i.32xlarge", + "c6i.large", + "c6i.xlarge", + "c6i.2xlarge", + "c6i.4xlarge", + "c6i.8xlarge", + "c6i.12xlarge", + "c6i.16xlarge", + "c6i.24xlarge", + "c6i.32xlarge", + "c6in.large", + "c6in.xlarge", + "c6in.2xlarge", + "c6in.4xlarge", + "c6in.8xlarge", + "c6in.12xlarge", + "c6in.16xlarge", + "c6in.24xlarge", + "c6in.32xlarge", + "r5.large", + "r5.xlarge", + "r5.2xlarge", + "r5.4xlarge", + "r5.8xlarge", + "r5.12xlarge", + "r5.16xlarge", + "r5.24xlarge", + "r5a.large", + "r5a.xlarge", + "r5a.2xlarge", + "r5a.4xlarge", + "r5a.8xlarge", + "r5a.12xlarge", + "r5a.16xlarge", + "r5a.24xlarge", + "r5b.large", + "r5b.xlarge", + "r5b.2xlarge", + "r5b.4xlarge", + "r5b.8xlarge", + "r5b.12xlarge", + "r5b.16xlarge", + "r5b.24xlarge", + "r5n.large", + "r5n.xlarge", + "r5n.2xlarge", + "r5n.4xlarge", + "r5n.8xlarge", + "r5n.12xlarge", + "r5n.16xlarge", + "r5n.24xlarge", + "r6i.large", + "r6i.xlarge", + "r6i.2xlarge", + "r6i.4xlarge", + "r6i.8xlarge", + "r6i.12xlarge", + "r6i.16xlarge", + "r6i.24xlarge", + "r6i.32xlarge", + "m6a.large", + "m6a.xlarge", + "m6a.2xlarge", + "m6a.4xlarge", + "m6a.8xlarge", + "m6a.12xlarge", + "m6a.16xlarge", + "m6a.24xlarge", + "m6a.32xlarge", + "m6a.48xlarge" + ] + mgmt_types = [ + "c5.large", + "c5.xlarge", + "c5.2xlarge", + "c5.4xlarge", + "c5.9xlarge", + "c5.12xlarge", + "c5.18xlarge", + "c5.24xlarge", + "c5n.large", + "c5n.xlarge", + "c5n.2xlarge", + "c5n.4xlarge", + "c5n.9xlarge", + "c5n.18xlarge", + "c5d.large", + "c5d.xlarge", + "c5d.2xlarge", + "c5d.4xlarge", + "c5d.9xlarge", + "c5d.12xlarge", + "c5d.18xlarge", + "c5d.24xlarge", + "m5.large", + "m5.xlarge", + "m5.2xlarge", + "m5.4xlarge", + "m5.8xlarge", + "m5.12xlarge", + "m5.16xlarge", + "m5.24xlarge", + "m6i.large", + "m6i.xlarge", + "m6i.2xlarge", + "m6i.4xlarge", + "m6i.8xlarge", + "m6i.12xlarge", + "m6i.16xlarge", + "m6i.24xlarge", + "m6i.32xlarge", + "c6i.large", + "c6i.xlarge", + "c6i.2xlarge", + "c6i.4xlarge", + "c6i.8xlarge", + "c6i.12xlarge", + "c6i.16xlarge", + "c6i.24xlarge", + "c6i.32xlarge", + "c6in.large", + "c6in.xlarge", + "c6in.2xlarge", + "c6in.4xlarge", + "c6in.8xlarge", + "c6in.12xlarge", + "c6in.16xlarge", + "c6in.24xlarge", + "c6in.32xlarge", + "r5.large", + "r5.xlarge", + "r5.2xlarge", + "r5.4xlarge", + "r5.8xlarge", + "r5.12xlarge", + "r5.16xlarge", + "r5.24xlarge", + "r5a.large", + "r5a.xlarge", + "r5a.2xlarge", + "r5a.4xlarge", + "r5a.8xlarge", + "r5a.12xlarge", + "r5a.16xlarge", + "r5a.24xlarge", + "r5b.large", + "r5b.xlarge", + "r5b.2xlarge", + "r5b.4xlarge", + "r5b.8xlarge", + "r5b.12xlarge", + "r5b.16xlarge", + "r5b.24xlarge", + "r5n.large", + "r5n.xlarge", + "r5n.2xlarge", + "r5n.4xlarge", + "r5n.8xlarge", + "r5n.12xlarge", + "r5n.16xlarge", + "r5n.24xlarge", + "r6i.large", + "r6i.xlarge", + "r6i.2xlarge", + "r6i.4xlarge", + "r6i.8xlarge", + "r6i.12xlarge", + "r6i.16xlarge", + "r6i.24xlarge", + "r6i.32xlarge", + "m6a.large", + "m6a.xlarge", + "m6a.2xlarge", + "m6a.4xlarge", + "m6a.8xlarge", + "m6a.12xlarge", + "m6a.16xlarge", + "m6a.24xlarge", + "m6a.32xlarge", + "m6a.48xlarge" + ] + mds_types = [ + "c5.large", + "c5.xlarge", + "c5.2xlarge", + "c5.4xlarge", + "c5.9xlarge", + "c5.12xlarge", + "c5.18xlarge", + "c5.24xlarge", + "c5n.large", + "c5n.xlarge", + "c5n.2xlarge", + "c5n.4xlarge", + "c5n.9xlarge", + "c5n.18xlarge", + "c5d.large", + "c5d.xlarge", + "c5d.2xlarge", + "c5d.4xlarge", + "c5d.9xlarge", + "c5d.12xlarge", + "c5d.18xlarge", + "c5d.24xlarge", + "m5.large", + "m5.xlarge", + "m5.2xlarge", + "m5.4xlarge", + "m5.8xlarge", + "m5.12xlarge", + "m5.16xlarge", + "m5.24xlarge", + "m6i.large", + "m6i.xlarge", + "m6i.2xlarge", + "m6i.4xlarge", + "m6i.8xlarge", + "m6i.12xlarge", + "m6i.16xlarge", + "m6i.24xlarge", + "m6i.32xlarge", + "c6i.large", + "c6i.xlarge", + "c6i.2xlarge", + "c6i.4xlarge", + "c6i.8xlarge", + "c6i.12xlarge", + "c6i.16xlarge", + "c6i.24xlarge", + "c6i.32xlarge", + "c6in.large", + "c6in.xlarge", + "c6in.2xlarge", + "c6in.4xlarge", + "c6in.8xlarge", + "c6in.12xlarge", + "c6in.16xlarge", + "c6in.24xlarge", + "c6in.32xlarge", + "r5.large", + "r5.xlarge", + "r5.2xlarge", + "r5.4xlarge", + "r5.8xlarge", + "r5.12xlarge", + "r5.16xlarge", + "r5.24xlarge", + "r5a.large", + "r5a.xlarge", + "r5a.2xlarge", + "r5a.4xlarge", + "r5a.8xlarge", + "r5a.12xlarge", + "r5a.16xlarge", + "r5a.24xlarge", + "r5b.large", + "r5b.xlarge", + "r5b.2xlarge", + "r5b.4xlarge", + "r5b.8xlarge", + "r5b.12xlarge", + "r5b.16xlarge", + "r5b.24xlarge", + "r5n.large", + "r5n.xlarge", + "r5n.2xlarge", + "r5n.4xlarge", + "r5n.8xlarge", + "r5n.12xlarge", + "r5n.16xlarge", + "r5n.24xlarge", + "r6i.large", + "r6i.xlarge", + "r6i.2xlarge", + "r6i.4xlarge", + "r6i.8xlarge", + "r6i.12xlarge", + "r6i.16xlarge", + "r6i.24xlarge", + "r6i.32xlarge", + "m6a.large", + "m6a.xlarge", + "m6a.2xlarge", + "m6a.4xlarge", + "m6a.8xlarge", + "m6a.12xlarge", + "m6a.16xlarge", + "m6a.24xlarge", + "m6a.32xlarge", + "m6a.48xlarge" + ] + server_types = [ + "t3.nano", + "t3.micro", + "t3.small", + "t3.medium", + "t3.large", + "t3.xlarge", + "t3.2xlarge" + ] +} + +locals { + gw_values = var.chkp_type == "gateway" ? local.gw_types : [] + mgmt_values = var.chkp_type == "management" ? local.mgmt_types : [] + mds_values = var.chkp_type == "mds" ? local.mds_types : [] + server_values = var.chkp_type == "server" ? local.server_types : [] + sa_values = var.chkp_type == "standalone" ? concat(local.gw_types, local.mgmt_types) : [] + allowed_values = coalescelist(local.gw_values, local.mgmt_values, local.mds_values, local.sa_values , local.server_types) + is_allowed_type = index(local.allowed_values, var.instance_type) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/instance_type/variables.tf b/deprecated/terraform/aws/R81/modules/common/instance_type/variables.tf new file mode 100755 index 00000000..1711c3f7 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/instance_type/variables.tf @@ -0,0 +1,22 @@ +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +locals { + type_allowed_values = [ + "gateway", + "management", + "mds", + "standalone", + "server" + ] + // Will fail if var.chkp_type is invalid + validate_instance_type = index(local.type_allowed_values, var.chkp_type) +} + +variable "instance_type" { + type = string + description = "AWS Instance type" +} + diff --git a/deprecated/terraform/aws/R81/modules/common/internal_default_route/locals.tf b/deprecated/terraform/aws/R81/modules/common/internal_default_route/locals.tf new file mode 100755 index 00000000..493c4d9a --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/internal_default_route/locals.tf @@ -0,0 +1,3 @@ +locals { + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/internal_default_route/main.tf b/deprecated/terraform/aws/R81/modules/common/internal_default_route/main.tf new file mode 100755 index 00000000..ddcb5bd8 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/internal_default_route/main.tf @@ -0,0 +1,6 @@ +resource "aws_route" "internal_default_route" { + count = local.internal_route_table_condition + route_table_id = var.private_route_table + destination_cidr_block = "0.0.0.0/0" + network_interface_id = var.internal_eni_id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/internal_default_route/output.tf b/deprecated/terraform/aws/R81/modules/common/internal_default_route/output.tf new file mode 100755 index 00000000..fa691b92 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/internal_default_route/output.tf @@ -0,0 +1,3 @@ +output "internal_default_route_id" { + value = aws_route.internal_default_route.*.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/internal_default_route/variables.tf b/deprecated/terraform/aws/R81/modules/common/internal_default_route/variables.tf new file mode 100755 index 00000000..b8e2f458 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/internal_default_route/variables.tf @@ -0,0 +1,9 @@ +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Gateway instance in the specified route table (e.g. rtb-12a34567)" + default="" +} +variable "internal_eni_id" { + type = string + description = "The internal-eni of the security gateway" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/load_balancer/main.tf b/deprecated/terraform/aws/R81/modules/common/load_balancer/main.tf new file mode 100755 index 00000000..18b3b753 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/load_balancer/main.tf @@ -0,0 +1,36 @@ +resource "random_id" "unique_lb_id" { + keepers = { + prefix = var.prefix_name + } + byte_length = 8 +} +resource "aws_lb" "load_balancer" { + name = substr(format("%s-%s", "${var.prefix_name}-LB", random_id.unique_lb_id.hex), 0, 32) + load_balancer_type = var.load_balancers_type == "gateway" ? "gateway" : var.load_balancers_type == "Network Load Balancer" ? "network": "application" + internal = var.load_balancers_type == "gateway" ? "false" : var.internal + subnets = var.instances_subnets + security_groups = var.security_groups + tags = var.tags + enable_cross_zone_load_balancing = var.cross_zone_load_balancing +} +resource "aws_lb_target_group" "lb_target_group" { + name = substr(format("%s-%s", "${var.prefix_name}-TG", random_id.unique_lb_id.hex), 0, 32) + vpc_id = var.vpc_id + protocol = var.load_balancer_protocol + port = var.target_group_port + health_check { + port = var.load_balancers_type != "gateway" ? var.health_check_port : 8117 + protocol = var.load_balancers_type != "gateway" ? var.health_check_protocol : "TCP" + } +} +resource "aws_lb_listener" "lb_listener" { + depends_on = [aws_lb.load_balancer, aws_lb_target_group.lb_target_group] + load_balancer_arn = aws_lb.load_balancer.arn + certificate_arn = var.certificate_arn + protocol = var.load_balancers_type != "gateway" ? var.load_balancer_protocol : null + port = var.load_balancers_type != "gateway" ? var.listener_port : null + default_action { + type = "forward" + target_group_arn = aws_lb_target_group.lb_target_group.arn + } +} diff --git a/deprecated/terraform/aws/R81/modules/common/load_balancer/output.tf b/deprecated/terraform/aws/R81/modules/common/load_balancer/output.tf new file mode 100755 index 00000000..63123606 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/load_balancer/output.tf @@ -0,0 +1,18 @@ +output "load_balancer_id" { + value = aws_lb.load_balancer.id +} +output "load_balancer_arn" { + value = aws_lb.load_balancer.arn +} +output "load_balancer_url" { + value = aws_lb.load_balancer.dns_name +} +output "target_group_id" { + value = aws_lb_target_group.lb_target_group.id +} +output "target_group_arn" { + value = aws_lb_target_group.lb_target_group.arn +} +output "load_balancer_tags" { + value = aws_lb.load_balancer.tags +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/load_balancer/variables.tf b/deprecated/terraform/aws/R81/modules/common/load_balancer/variables.tf new file mode 100755 index 00000000..2e143fc7 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/load_balancer/variables.tf @@ -0,0 +1,62 @@ +variable "instances_subnets" { + type = list(string) + description = "Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} +variable "prefix_name" { + type = string + description = "Load Balancer and Target Group prefix name" + default = "quickstart" +} +variable "internal" { + type = bool + description = "Select 'true' to create an Internal Load Balancer." + default = false +} +variable "security_groups" { + type = list(string) + description = "A list of security group IDs to assign to the LB. Only valid for Load Balancers of type application" +} +variable "tags" { + type = map(string) + description = "A map of tags to assign to the load balancer." +} +variable "vpc_id" { + type = string +} +variable "load_balancers_type" { + type = string + description = "Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing" + default = "Network Load Balancer" +} +variable "load_balancer_protocol" { + type = string + description = "The protocol to use on the Load Balancer." +} +variable "target_group_port" { + type = number + description = "The port on which targets receive traffic." +} +variable "listener_port" { + type = string + description = "The port on which the load balancer is listening." +} +variable "certificate_arn" { + type = string + description = "The ARN of the default server certificate. Exactly one certificate is required if the protocol is HTTPS or TLS. " + default = "" +} +variable "cross_zone_load_balancing"{ + type = bool + default = false + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." +} +variable "health_check_port" { + description = "The health check port" + type = number + default = null +} +variable "health_check_protocol" { + description = "The health check protocol" + type = string + default = null +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/permissive_sg/main.tf b/deprecated/terraform/aws/R81/modules/common/permissive_sg/main.tf new file mode 100755 index 00000000..265f3c56 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/permissive_sg/main.tf @@ -0,0 +1,20 @@ +resource "aws_security_group" "permissive_sg" { + description = "Permissive security group" + vpc_id = var.vpc_id + egress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + name_prefix = format("%s-PermissiveSecurityGroup", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) // Group name + tags = { + Name = format("%s-PermissiveSecurityGroup", var.resources_tag_name != "" ? var.resources_tag_name : var.gateway_name) // Resource name + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/permissive_sg/output.tf b/deprecated/terraform/aws/R81/modules/common/permissive_sg/output.tf new file mode 100755 index 00000000..83541c15 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/permissive_sg/output.tf @@ -0,0 +1,9 @@ +output "permissive_sg_id" { + value = aws_security_group.permissive_sg.id +} +output "permissive_sg_name" { + value = aws_security_group.permissive_sg.name +} +output "permissive_sg_arn" { + value = aws_security_group.permissive_sg.arn +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/permissive_sg/variables.tf b/deprecated/terraform/aws/R81/modules/common/permissive_sg/variables.tf new file mode 100755 index 00000000..d2afaad2 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/permissive_sg/variables.tf @@ -0,0 +1,13 @@ +variable "vpc_id" { + type = string +} +variable "resources_tag_name" { + type = string + description = "(Optional)" + default = "" +} +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway-tf" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/common/version_license/main.tf b/deprecated/terraform/aws/R81/modules/common/version_license/main.tf new file mode 100755 index 00000000..c8fe1838 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/version_license/main.tf @@ -0,0 +1,60 @@ +locals { + gw_versions = [ + "R81-BYOL", + "R81-PAYG-NGTP", + "R81-PAYG-NGTX", + "R81.10-BYOL", + "R81.10-PAYG-NGTP", + "R81.10-PAYG-NGTX", + "R81.20-BYOL", + "R81.20-PAYG-NGTP", + "R81.20-PAYG-NGTX", + "R82-BYOL", + "R82-PAYG-NGTP", + "R82-PAYG-NGTX" + ] + mgmt_versions = [ + "R81-BYOL", + "R81-PAYG", + "R81.10-BYOL", + "R81.10-PAYG", + "R81.20-BYOL", + "R81.20-PAYG", + "R82-BYOL", + "R82-PAYG" + ] + mds_versions = [ + "R81-BYOL", + "R81.10-BYOL", + "R81.20-BYOL", + "R82-BYOL" + ] + standalone_versions = [ + "R81-BYOL", + "R81-PAYG-NGTP", + "R81.10-BYOL", + "R81.10-PAYG-NGTP", + "R81.20-BYOL", + "R81.20-PAYG-NGTP", + "R82-BYOL", + "R82-PAYG-NGTP" + ] + gwlb_gw_versions = [ + "R81.20-BYOL", + "R81.20-PAYG-NGTP", + "R81.20-PAYG-NGTX", + "R82-BYOL", + "R82-PAYG-NGTP", + "R82-PAYG-NGTX" + ] +} + +locals { + gw_values = var.chkp_type == "gateway" ? local.gw_versions : [] + mgmt_values = var.chkp_type == "management" ? local.mgmt_versions : [] + mds_values = var.chkp_type == "mds" ? local.mds_versions : [] + standalone_values = var.chkp_type == "standalone" ? local.standalone_versions : [] + gwlb_gw_values = var.chkp_type == "gwlb_gw" ? local.gwlb_gw_versions : [] + allowed_values = coalescelist(local.gw_values, local.mgmt_values, local.standalone_values, local.mds_values, local.gwlb_gw_values) + is_allowed_type = index(local.allowed_values, var.version_license) +} diff --git a/deprecated/terraform/aws/R81/modules/common/version_license/variables.tf b/deprecated/terraform/aws/R81/modules/common/version_license/variables.tf new file mode 100755 index 00000000..9467e232 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/common/version_license/variables.tf @@ -0,0 +1,21 @@ +variable "chkp_type" { + type = string + description = "The Check Point machine type" + default = "gateway" +} +locals { + type_allowed_values = [ + "gateway", + "management", + "mds", + "standalone", + "gwlb_gw"] + // Will fail if var.chkp_type is invalid + validate_chkp_type = index(local.type_allowed_values, var.chkp_type) +} + +variable "version_license" { + type = string + description = "AWS Version license" +} + diff --git a/deprecated/terraform/aws/R81/modules/custom-autoscale/locals.tf b/deprecated/terraform/aws/R81/modules/custom-autoscale/locals.tf new file mode 100755 index 00000000..1a9b6900 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/custom-autoscale/locals.tf @@ -0,0 +1,9 @@ +locals { + asg_name = format("%s%s-servers", var.prefix != "" ? format("%s-", var.prefix) : "", var.asg_name) + + regex_valid_server_ami = "^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$" + // Will fail if var.server_ami is invalid + regex_server_ami = regex(local.regex_valid_server_ami, var.server_ami) == var.server_ami ? 0 : "Amazon Machine Image ID must be in the form ami-xxxxxxxx or ami-xxxxxxxxxxxxxxxxx" + + provided_target_groups_condition = var.servers_target_groups != "" ? true : false +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/custom-autoscale/main.tf b/deprecated/terraform/aws/R81/modules/custom-autoscale/main.tf new file mode 100755 index 00000000..c361388d --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/custom-autoscale/main.tf @@ -0,0 +1,94 @@ +resource "aws_security_group" "servers_security_group" { + count = var.deploy_internal_security_group ? 1 : 0 + name_prefix = format("%s_ServersSecurityGroup", local.asg_name) + description = "Servers security group" + vpc_id = var.vpc_id + + ingress { + from_port = 0 + to_port = 0 + protocol = "-1" + cidr_blocks = ["0.0.0.0/0"] + } + + tags = { + Name = format("%s_ServersSecurityGroup", local.asg_name) + } +} + + +resource "aws_launch_template" "servers_launch_template" { + name_prefix = local.asg_name + network_interfaces { + associate_public_ip_address = var.allocate_public_address + security_groups = var.deploy_internal_security_group ? [aws_security_group.servers_security_group[0].id] : [var.source_security_group] + } + key_name = var.key_name + image_id = var.server_ami + description = "Initial template version" + monitoring { + enabled = true + } + instance_type = var.servers_instance_type +} +resource "aws_autoscaling_group" "servers_group" { + name_prefix = local.asg_name + vpc_zone_identifier = var.servers_subnets + launch_template { + name = aws_launch_template.servers_launch_template.name + version = aws_launch_template.servers_launch_template.latest_version + } + min_size = var.servers_min_group_size + max_size = var.servers_max_group_size + target_group_arns = local.provided_target_groups_condition ? [var.servers_target_groups] : [] + + tag { + key = "Name" + value = format("%s%s", var.prefix != "" ? format("%s-", var.prefix) : "", var.server_name) + propagate_at_launch = true + } +} +resource "aws_autoscaling_policy" "scale_up_policy" { + adjustment_type = "ChangeInCapacity" + autoscaling_group_name = aws_autoscaling_group.servers_group.name + name = "scale_up_policy" + cooldown = 300 + scaling_adjustment = 1 +} +resource "aws_autoscaling_policy" "scale_down_policy" { + adjustment_type = "ChangeInCapacity" + autoscaling_group_name = aws_autoscaling_group.servers_group.name + name = "scale_down_policy" + cooldown = 300 + scaling_adjustment = -1 +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_high" { + alarm_description = "Scale-up if CPU > 80% for 10 minutes" + metric_name = "CPUUtilization" + namespace = "AWS/EC2" + statistic = "Average" + period = "300" + evaluation_periods = "2" + threshold = "80" + alarm_actions = [aws_autoscaling_policy.scale_up_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.servers_group.name + } + comparison_operator = "GreaterThanThreshold" + alarm_name = "cpu_alarm_high" +} +resource "aws_cloudwatch_metric_alarm" "cpu_alarm_low" { + alarm_description = "Scale-down if CPU < 60% for 10 minutes" + metric_name = "CPUUtilization" + namespace = "AWS/EC2" + statistic = "Average" + period = "300" + evaluation_periods = "2" + threshold = "60" + alarm_actions = [aws_autoscaling_policy.scale_down_policy.arn] + dimensions = { + AutoScalingGroupName = aws_autoscaling_group.servers_group.name + } + comparison_operator = "LessThanThreshold" + alarm_name = "cpu_alarm_low" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/custom-autoscale/variables.tf b/deprecated/terraform/aws/R81/modules/custom-autoscale/variables.tf new file mode 100755 index 00000000..a99cb9a5 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/custom-autoscale/variables.tf @@ -0,0 +1,89 @@ +// Module: Auto Scaling group of workload servers + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string + description = "Select an existing VPC" +} +variable "servers_subnets" { + type = list(string) + description = "Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-0d72417c,subnet-1f61306f,subnet-1061d06f)" +} + +// --- EC2 Instances Configuration --- +variable "server_ami" { + type = string + description = "The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63)" +} +variable "server_name" { + type = string + description = "AMI of the servers" + default = "Server-tf" +} +variable "servers_instance_type" { + type = string + description = "The EC2 instance type for the web servers" + default = "t3.micro" +} +module "validate_servers_instance_type" { + source = "../common/instance_type" + + chkp_type = "server" + instance_type = var.servers_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "allocate_public_address" { + type = bool + description = "Allocate an elastic IP for each server" + default = false +} + +// --- Auto Scaling Configuration --- +variable "servers_min_group_size" { + type = number + description = "The minimal number of servers in the Auto Scaling group" + default = 2 +} +resource "null_resource" "servers_min_group_size_too_small" { + // servers_min_group_size validation - resource will not be created if the size is smaller than 1 + count = var.servers_min_group_size >= 1 ? 0 : "servers_min_group_size must be at least 1" +} +variable "servers_max_group_size" { + type = number + description = "The maximal number of servers in the Auto Scaling group" + default = 10 +} +resource "null_resource" "servers_max_group_size_too_small" { + // servers_max_group_size validation - resource will not be created if the size is smaller than 1 + count = var.servers_max_group_size >= 1 ? 0 : "servers_max_group_size must be at least 1" +} +variable "servers_target_groups" { + type = string + description = "(Optional) An optional list of Target Groups to associate with the Auto Scaling group (comma separated list of ARNs, without spaces)" + default = "" +} +variable "deploy_internal_security_group" { + type = bool + description = "Select 'false' to use an existing Security group" + default = true +} +variable "source_security_group" { + type = string + description = "The ID of Security Group from which access will be allowed to the instances in this Auto Scaling group" + default = "" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/modules/vpc/main.tf b/deprecated/terraform/aws/R81/modules/vpc/main.tf new file mode 100755 index 00000000..b4b223b8 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/vpc/main.tf @@ -0,0 +1,66 @@ +// --- VPC --- +resource "aws_vpc" "vpc" { + cidr_block = var.vpc_cidr +} + +// --- Internet Gateway --- +resource "aws_internet_gateway" "igw" { + vpc_id = aws_vpc.vpc.id +} + +// --- Public Subnets --- +resource "aws_subnet" "public_subnets" { + for_each = var.public_subnets_map + + vpc_id = aws_vpc.vpc.id + availability_zone = each.key + cidr_block = cidrsubnet(aws_vpc.vpc.cidr_block, var.subnets_bit_length, each.value) + map_public_ip_on_launch = true + tags = { + Name = format("Public subnet %s", each.value) + } +} + +// --- Private Subnets --- +resource "aws_subnet" "private_subnets" { + for_each = var.private_subnets_map + + vpc_id = aws_vpc.vpc.id + availability_zone = each.key + cidr_block = cidrsubnet(aws_vpc.vpc.cidr_block, var.subnets_bit_length, each.value) + tags = { + Name = format("Private subnet %s", each.value) + } +} + +// --- tgw Subnets --- +resource "aws_subnet" "tgw_subnets" { + for_each = var.tgw_subnets_map + + vpc_id = aws_vpc.vpc.id + availability_zone = each.key + cidr_block = cidrsubnet(aws_vpc.vpc.cidr_block, var.subnets_bit_length, each.value) + tags = { + Name = format("tgw subnet %s", each.value) + } +} + + +// --- Routes --- +resource "aws_route_table" "public_subnet_rtb" { + vpc_id = aws_vpc.vpc.id + tags = { + Name = "Public Subnets Route Table" + } +} +resource "aws_route" "vpc_internet_access" { + route_table_id = aws_route_table.public_subnet_rtb.id + destination_cidr_block = "0.0.0.0/0" + gateway_id = aws_internet_gateway.igw.id +} +resource "aws_route_table_association" "public_rtb_to_public_subnets" { + for_each = { for public_subnet in aws_subnet.public_subnets : public_subnet.cidr_block => public_subnet.id } + route_table_id = aws_route_table.public_subnet_rtb.id + subnet_id = each.value +} + diff --git a/deprecated/terraform/aws/R81/modules/vpc/output.tf b/deprecated/terraform/aws/R81/modules/vpc/output.tf new file mode 100755 index 00000000..fc4173c9 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/vpc/output.tf @@ -0,0 +1,18 @@ +output "vpc_id" { + value = aws_vpc.vpc.id +} +output "public_subnets_ids_list" { + value = [for public_subnet in aws_subnet.public_subnets : public_subnet.id ] +} +output "private_subnets_ids_list" { + value = [for private_subnet in aws_subnet.private_subnets : private_subnet.id] +} +output "tgw_subnets_ids_list" { + value = [for tgw_subnet in aws_subnet.tgw_subnets : tgw_subnet.id] +} +output "public_rtb" { + value = aws_route_table.public_subnet_rtb.id +} +output "aws_igw" { + value = aws_internet_gateway.igw.id +} diff --git a/deprecated/terraform/aws/R81/modules/vpc/variables.tf b/deprecated/terraform/aws/R81/modules/vpc/variables.tf new file mode 100755 index 00000000..2623f9d0 --- /dev/null +++ b/deprecated/terraform/aws/R81/modules/vpc/variables.tf @@ -0,0 +1,22 @@ +variable "vpc_cidr" { + type = string +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "tgw_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + default = {} +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20." +} + diff --git a/deprecated/terraform/aws/R81/qs-autoscale-master/README.md b/deprecated/terraform/aws/R81/qs-autoscale-master/README.md new file mode 100755 index 00000000..8bffc621 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale-master/README.md @@ -0,0 +1,256 @@ +# Check Point CloudGuard Network Quick Start Auto Scaling Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group in a new VPC. + +These types of Terraform resources are supported: +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Subnet](https://www.terraform.io/docs/providers/aws/r/subnet.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Load Balancer](https://www.terraform.io/docs/providers/aws/r/lb.html) +* [Load Balancer Target Group](https://www.terraform.io/docs/providers/aws/r/lb_target_group.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Check Point CloudGuard Auto Scaling on AWS](https://aws.amazon.com/quickstart/architecture/check-point-cloudguard/) for additional information + +This solution uses the following modules: +- /terraform/aws/qs-autoscale +- /terraform/aws/autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/qs-autoscale, /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/qs-autoscale, /terraform/aws/autoscale and /terraform/aws/management: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/qs-autoscale-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/qs-autoscale-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "TF" + asg_name = "asg-qs" + + // --- Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 + } + subnets_bit_length = 8 + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + provision_tag = "quickstart" + load_balancers_type = "Network Load Balancer" + LB_protocol = "TCP" + certificate = "arn:aws:iam::12345678:server-certificate/certificate" + service_port = "80" + admin_shell = "/etc/cli.sh" + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = false + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + + // --- Web Servers Auto Scaling Group Configuration --- + servers_deploy = true + servers_instance_type = "t3.micro" + server_ami = "ami-12345abc" + ``` + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` + - To deploy web servers: + ``` + servers_deploy = true + ``` + - To create an ASG configuration without a proxy ELB: + ``` + proxy_elb_type= "none" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| provision_tag | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | quickstart | no | +| load_balancers_type | Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing | string | - Network Load Balancer
- Application Load Balancer
| Network Load Balancer | no | +| load_balancer_protocol | The protocol to use on the Load Balancer | string | Network Load Balancer:
- TCP
- TLS
- UDP
- TCP_UDP

Application Load Balancer:
- HTTP
- HTTPS | TCP | yes | +| certificate | Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP | string | n/a | n/a | no | +| service_port | The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS | string | n/a | n/a | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | list(string) | n/a | n/a | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| servers_deploy | Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored | bool | true/false | false | no | +| servers_subnets | Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-0d72417c,subnet-1f61306f,subnet-1061d06f). | list(string) | n/a | n/a | yes | +| servers_instance_type | The EC2 instance type for the web servers | string | - t3.nano
- t3.micro
- t3.small
- t3.medium
- t3.large
- t3.xlarge
- t3.2xlarge | t3.micro | no | +| server_ami | The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63) | string | n/a | n/a | yes | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + + +## Outputs +| Name | Description | +|----------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| public_subnets_ids_list | A list of the public subnets ids | +| private_subnets_ids_list | A list of the private subnets ids | +| public_rout_table | The public route table id | +| internal_port | The internal Load Balancer should listen to this port | +| management_name | The deployed Security Management AWS instance name | +| load_balancer_url | The URL of the external Load Balancer | +| external_load_balancer_arn | The external Load Balancer ARN | +| internal_load_balancer_arn | The internal Load Balancer ARN | +| external_lb_target_group_arn | The external Load Balancer Target Group ARN | +| internal_lb_target_group_arn | The internal Load Balancer Target Group ARN | +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------| +| 20240425 | Remove support for R81 and lower versions | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231127 | Add support for parameter admin shell | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Quick Start Auto Scaling Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/qs-autoscale-master/locals.tf b/deprecated/terraform/aws/R81/qs-autoscale-master/locals.tf new file mode 100755 index 00000000..e23f58a2 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale-master/locals.tf @@ -0,0 +1,63 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + regex_valid_provision_tag = "^[a-zA-Z0-9-]{1,12}$" + // Will fail if var.provision_tag is invalid + regex_provision_tag = regex(local.regex_valid_provision_tag, var.provision_tag) == var.provision_tag ? 0 : "Variable [provision_tag] must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + + load_balancers_type_allowed_values = [ + "Network Load Balancer", + "Application Load Balancer"] + // Will fail if var.load_balancers_type is invalid + validate_load_balancers_type = index(local.load_balancers_type_allowed_values, var.load_balancers_type) + + lb_protocol_allowed_values = var.load_balancers_type == "Network Load Balancer" ? [ + "TCP", + "TLS", + "UDP", + "TCP_UDP"] : [ + "HTTP", + "HTTPS"] + // Will fail if var.load_balancer_protocol is invalid + validate_lb_protocol = index(local.lb_protocol_allowed_values, var.load_balancer_protocol) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_certificate = "^(arn:aws:[a-z]+::[0-9]{12}:server-certificate/[a-zA-Z0-9-]*)?$" + // Will fail if var.certificate is invalid + regex_certificate = regex(local.regex_valid_certificate, var.certificate) == var.certificate ? 0 : "Variable [certificate] must be a valid Amazon Resource Name (ARN), for example: arn:aws:iam::123456789012:server-certificate/web-server-certificate" + + regex_valid_service_port = "^([0-9]{1,4}|[1-5][0-9]{4}|6[0-4][0-9]{3}|65[0-4][0-9]{2}|655[0-2][0-9]|6553[0-5])?$" + // Will fail if var.service_port is invalid + regex_service_port = regex(local.regex_valid_service_port, var.service_port) == var.service_port ? 0 : "Custom service port must be a number between 0 and 65535" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash." + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters." + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash." + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR." + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses." + + + regex_valid_server_ami = "^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$" + // Will fail if var.server_ami is invalid + regex_server_ami = regex(local.regex_valid_server_ami, var.server_ami) == var.server_ami ? 0 : "Amazon Machine Image ID must be in the form ami-xxxxxxxx or ami-xxxxxxxxxxxxxxxxx" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/qs-autoscale-master/main.tf b/deprecated/terraform/aws/R81/qs-autoscale-master/main.tf new file mode 100755 index 00000000..9c7eada0 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale-master/main.tf @@ -0,0 +1,60 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +module "launch_qs_autoscale" { + source = "../qs-autoscale" + providers = { + aws = aws + } + + region = var.region + prefix = var.prefix + asg_name = var.asg_name + vpc_id = module.launch_vpc.vpc_id + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + provision_tag = var.provision_tag + load_balancers_type = var.load_balancers_type + load_balancer_protocol = var.load_balancer_protocol + certificate = var.certificate + service_port = var.service_port + admin_shell = var.admin_shell + gateways_subnets = module.launch_vpc.public_subnets_ids_list + gateway_instance_type = var.gateway_instance_type + gateways_min_group_size = var.gateways_min_group_size + gateways_max_group_size = var.gateways_max_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + enable_cloudwatch = var.enable_cloudwatch + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.gateway_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateways_blades = var.gateways_blades + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + servers_deploy= var.servers_deploy + servers_subnets = module.launch_vpc.private_subnets_ids_list + servers_instance_type = var.servers_instance_type + server_ami = var.server_ami +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/qs-autoscale-master/output.tf b/deprecated/terraform/aws/R81/qs-autoscale-master/output.tf new file mode 100755 index 00000000..1130dfe0 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale-master/output.tf @@ -0,0 +1,58 @@ +output "Deployment" { + value = module.launch_qs_autoscale.Deployment +} + +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "private_subnets_ids_list" { + value = module.launch_vpc.private_subnets_ids_list +} +output "public_rout_table" { + value = module.launch_vpc.public_rtb +} + +output "management_name" { + value = module.launch_qs_autoscale.management_name +} +output "internal_port" { + value = module.launch_qs_autoscale.internal_port +} +output "load_balancer_url" { + value = module.launch_qs_autoscale.load_balancer_url +} +output "external_load_balancer_arn" { + value = module.launch_qs_autoscale.external_load_balancer_arn +} +output "internal_load_balancer_arn" { + value = module.launch_qs_autoscale.internal_load_balancer_arn +} +output "external_lb_target_group_arn" { + value = module.launch_qs_autoscale.external_lb_target_group_arn +} +output "internal_lb_target_group_arn" { + value = module.launch_qs_autoscale.internal_lb_target_group_arn +} + +output "autoscale_autoscaling_group_name" { + value = module.launch_qs_autoscale.autoscale_autoscaling_group_name +} +output "autoscale_autoscaling_group_arn" { + value = module.launch_qs_autoscale.autoscale_autoscaling_group_arn +} +output "autoscale_security_group_id" { + value = module.launch_qs_autoscale.autoscale_security_group_id +} +output "autoscale_iam_role_name" { + value = module.launch_qs_autoscale.autoscale_iam_role_name +} + +output "configuration_template" { + value = module.launch_qs_autoscale.configuration_template +} +output "controller_name" { + value = module.launch_qs_autoscale.controller_name +} diff --git a/deprecated/terraform/aws/R81/qs-autoscale-master/terraform.tfvars b/deprecated/terraform/aws/R81/qs-autoscale-master/terraform.tfvars new file mode 100755 index 00000000..37a07774 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale-master/terraform.tfvars @@ -0,0 +1,57 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "TF" +asg_name = "asg-qs" + +// --- Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 +} +subnets_bit_length = 8 + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +provision_tag = "quickstart" +load_balancers_type = "Application Load Balancer" +load_balancer_protocol = "HTTP" +certificate = "" +service_port = "80" +admin_shell = "/etc/cli.sh" + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Web Servers Auto Scaling Group Configuration --- +servers_deploy = true +servers_instance_type = "t3.micro" +server_ami = "ami-12345abc" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/qs-autoscale-master/variables.tf b/deprecated/terraform/aws/R81/qs-autoscale-master/variables.tf new file mode 100755 index 00000000..317b1c94 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale-master/variables.tf @@ -0,0 +1,240 @@ +// Module: Check Point CloudGuard Network Quick Start Auto Scaling +//Deploy a Check Point CloudGuard Network Security Gateways Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group in a new VPC. + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} +// --- Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "provision_tag" { + type = string + description = "The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + default = "quickstart" +} +variable "load_balancers_type" { + type = string + description = "Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing" + default = "Network Load Balancer" +} +variable "load_balancer_protocol" { + type = string + description = "The protocol to use on the Load Balancer" +} +variable "certificate" { + type = string + description = "Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP" +} +variable "service_port" { + type = string + description = "The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS" +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Web Servers Auto Scaling Group Configuration --- +variable "servers_deploy" { + type = bool + description = "Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored" + default = false +} +variable "servers_instance_type" { + type = string + description = "The EC2 instance type for the web servers" + default = "t3.micro" +} +module "validate_servers_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "server" + instance_type = var.servers_instance_type +} +variable "server_ami" { + type = string + description = "The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63)" +} diff --git a/deprecated/terraform/aws/R81/qs-autoscale-master/versions.tf b/deprecated/terraform/aws/R81/qs-autoscale-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/qs-autoscale/README.md b/deprecated/terraform/aws/R81/qs-autoscale/README.md new file mode 100755 index 00000000..b86ceddd --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale/README.md @@ -0,0 +1,238 @@ +# Check Point CloudGuard Network Quick Start Auto Scaling Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Load Balancer](https://www.terraform.io/docs/providers/aws/r/lb.html) +* [Load Balancer Target Group](https://www.terraform.io/docs/providers/aws/r/lb_target_group.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Check Point CloudGuard Auto Scaling on AWS](https://aws.amazon.com/quickstart/architecture/check-point-cloudguard/) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale +- /terraform/aws/modules/custom-autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/qs-autoscale/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Environment --- + prefix = "TF" + asg_name = "asg-qs" + + // --- General Settings --- + vpc_id = "vpc-12345678" + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + provision_tag = "quickstart" + load_balancers_type = "Application Load Balancer" + load_balancer_protocol = "HTTP" + certificate = "" + service_port = "80" + admin_shell = "/etc/cli.sh" + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = true + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + + // --- Web Servers Auto Scaling Group Configuration --- + servers_deploy = false + servers_subnets = ["subnet-1234abcd", "subnet-56789def"] + servers_instance_type = "t3.micro" + server_ami = "ami-12345678" + ``` + +- Conditional creation + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` + - To deploy web servers: + ``` + servers_deploy = true + ``` + - To create an ASG configuration without a proxy ELB: + ``` + proxy_elb_type= "none" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| prefix | (Optional) Instances name prefix | string | n/a | "" | no | +| asg_name | Autoscaling Group name | string | n/a | Check-Point-ASG-tf | no | +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| provision_tag | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | quickstart | no | +| load_balancers_type | Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing | string | - Network Load Balancer
- Application Load Balancer
| Network Load Balancer | no | +| load_balancer_protocol | The protocol to use on the Load Balancer | string | Network Load Balancer:
- TCP
- TLS
- UDP
- TCP_UDP

Application Load Balancer:
- HTTP
- HTTPS | TCP | yes | +| certificate | Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP | string | n/a | n/a | no | +| service_port | The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS | string | n/a | n/a | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | list(string) | n/a | n/a | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| servers_deploy | Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored | bool | true/false | false | no | +| servers_subnets | Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-0d72417c,subnet-1f61306f,subnet-1061d06f). | list(string) | n/a | n/a | yes | +| servers_instance_type | The EC2 instance type for the web servers | string | - t3.nano
- t3.micro
- t3.small
- t3.medium
- t3.large
- t3.xlarge
- t3.2xlarge | t3.micro | no | +| server_ami | The Amazon Machine Image ID of a preconfigured web server (e.g. ami-0dc7dc63) | string | n/a | n/a | yes | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|----------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| management_name | The deployed Security Management AWS instance name | +| internal_port | The internal Load Balancer should listen to this port | +| load_balancer_url | The URL of the external Load Balancer | +| external_load_balancer_arn | The external Load Balancer ARN | +| internal_load_balancer_arn | The internal Load Balancer ARN | +| external_LB_target_group_arn | The external Load Balancer Target Group ARN | +| internal_LB_target_group_arn | The internal Load Balancer Target Group ARN | +| autoscale_autoscaling_group_name | The name of the deployed AutoScaling Group | +| autoscale_autoscaling_group_arn | The ARN for the deployed AutoScaling Group | +| autoscale_security_group_id | The deployed AutoScaling Group's security group id | +| autoscale_iam_role_name | The deployed AutoScaling Group's IAM role name (if created) | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------------------------| +| 20240425 | Remove support for R81 and lower versions | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20240130 | Network Load Balancer Health Check configuration change for higher than R81 version. New Health Check Port is 8117 and Protocol TCP | +| 20231127 | Add support for parameter admin shell | +| 20231022 | Fixed template to populate x-chkp-tags correctly | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Quick Start Auto Scaling Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/qs-autoscale/locals.tf b/deprecated/terraform/aws/R81/qs-autoscale/locals.tf new file mode 100755 index 00000000..2ecac5dd --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale/locals.tf @@ -0,0 +1,71 @@ +locals { + load_balancer_name = format("%sLB", var.prefix != "" ? format("%s-", var.prefix) : "") + target_group_name = format("%sTG", var.prefix != "" ? format("%s-", var.prefix) : "") + regex_valid_provision_tag = "^[a-zA-Z0-9-]{1,12}$" + // Will fail if var.provision_tag is invalid + regex_provision_tag = regex(local.regex_valid_provision_tag, var.provision_tag) == var.provision_tag ? 0 : "Variable [provision_tag] must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + + load_balancers_type_allowed_values = [ + "Network Load Balancer", + "Application Load Balancer" + ] + // Will fail if var.load_balancers_type is invalid + validate_load_balancers_type = index(local.load_balancers_type_allowed_values, var.load_balancers_type) + + lb_protocol_allowed_values = var.load_balancers_type == "Network Load Balancer" ? [ + "TCP", + "TLS", + "UDP", + "TCP_UDP" + ] : [ + "HTTP", + "HTTPS" + ] + // Will fail if var.load_balancer_protocol is invalid + validate_lb_protocol = index(local.lb_protocol_allowed_values, var.load_balancer_protocol) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_certificate = "^(arn:aws:[a-z]+::[0-9]{12}:server-certificate/[a-zA-Z0-9-]*)?$" + // Will fail if var.certificate is invalid + regex_certificate = regex(local.regex_valid_certificate, var.certificate) == var.certificate ? 0 : "Variable [certificate] must be a valid Amazon Resource Name (ARN), for example: arn:aws:iam::123456789012:server-certificate/web-server-certificate" + + regex_valid_service_port = "^([0-9]{1,4}|[1-5][0-9]{4}|6[0-4][0-9]{3}|65[0-4][0-9]{2}|655[0-2][0-9]|6553[0-5])?$" + // Will fail if var.service_port is invalid + regex_service_port = regex(local.regex_valid_service_port, var.service_port) == var.service_port ? 0 : "Custom service port must be a number between 0 and 65535" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash." + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters." + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash." + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR." + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses." + + regex_valid_server_ami = "^(ami-(([0-9a-f]{8})|([0-9a-f]{17})))?$" + // Will fail if var.server_ami is invalid + regex_server_ami = regex(local.regex_valid_server_ami, var.server_ami) == var.server_ami ? 0 : "Amazon Machine Image ID must be in the form ami-xxxxxxxx or ami-xxxxxxxxxxxxxxxxx" + + alb_condition = var.load_balancers_type == "Application Load Balancer" + nlb_condition = var.load_balancers_type == "Network Load Balancer" + provided_port_condition = var.service_port != "" + encrypted_protocol_condition = (local.alb_condition && var.load_balancer_protocol == "HTTPS") || (local.nlb_condition && var.load_balancer_protocol == "TLS") ? true : false + deploy_management_condition = var.management_deploy == true + deploy_servers_condition = var.servers_deploy == true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/qs-autoscale/main.tf b/deprecated/terraform/aws/R81/qs-autoscale/main.tf new file mode 100755 index 00000000..7fa5f27f --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale/main.tf @@ -0,0 +1,165 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +resource "aws_security_group" "external_alb_security_group" { + count = local.alb_condition ? 1 : 0 + description = "External ALB security group" + vpc_id = var.vpc_id + + egress { + from_port = local.encrypted_protocol_condition ? 9443 : 9080 + protocol = "tcp" + to_port = local.encrypted_protocol_condition ? 9443 : 9080 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + protocol = "tcp" + to_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + cidr_blocks = ["0.0.0.0/0"] + } +} + +module "external_load_balancer" { + source = "../modules/common/load_balancer" + + load_balancers_type = var.load_balancers_type + instances_subnets = var.gateways_subnets + prefix_name = "${var.prefix}-External" + internal = false + security_groups = local.alb_condition ? [aws_security_group.external_alb_security_group[0].id] : [] + tags = {} + vpc_id = var.vpc_id + load_balancer_protocol = var.load_balancer_protocol + target_group_port = local.encrypted_protocol_condition ? 9443 : 9080 + listener_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? "443" : "80" + certificate_arn = local.encrypted_protocol_condition ? var.certificate : "" + health_check_port = var.load_balancers_type == "Network Load Balancer" ? 8117 : null + health_check_protocol = var.load_balancers_type == "Network Load Balancer" ? "TCP" : null +} + +module "autoscale" { + source = "../autoscale" + providers = { + aws = aws + } + + prefix = var.prefix + asg_name = var.asg_name + vpc_id = var.vpc_id + subnet_ids = var.gateways_subnets + gateway_name = "${var.provision_tag}-security-gateway" + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + metadata_imdsv2_required = var.metadata_imdsv2_required + minimum_group_size = var.gateways_min_group_size + maximum_group_size = var.gateways_max_group_size + target_groups = tolist([module.external_load_balancer.target_group_arn]) + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding quickstart identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: autoscale_qs' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"autoscale_qs\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo -e '\nFinished Bootstrap script\n'" + management_server = "${var.provision_tag}-management" + configuration_template = "${var.provision_tag}-template" +} + +data "aws_region" "current"{} + +module "management" { + providers = { + aws = aws + } + count = local.deploy_management_condition ? 1 : 0 + source = "../management" + + vpc_id = var.vpc_id + subnet_id = var.gateways_subnets[0] + management_name = "${var.provision_tag}-management" + management_instance_type = var.management_instance_type + key_name = var.key_name + volume_encryption = var.enable_volume_encryption ? "alias/aws/ebs" : "" + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + iam_permissions = "Create with read-write permissions" + management_version = var.management_version + admin_shell = var.admin_shell + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + allow_upload_download = var.allow_upload_download + admin_cidr = var.admin_cidr + gateway_addresses = var.gateways_addresses + management_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding quickstart identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: management_qs' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"management_qs\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo 'Creating CME configuration'; autoprov_cfg -f init AWS -mn ${var.provision_tag}-management -tn ${var.provision_tag}-template -cn ${var.provision_tag}-controller -po ${var.gateways_policy} -otp ${var.gateway_SICKey} -r ${data.aws_region.current.name} -ver ${split("-", var.gateway_version)[0]} -iam; ${var.gateways_blades} && autoprov_cfg -f set template -tn ${var.provision_tag}-template -ips -appi -av -ab; echo -e '\nFinished Bootstrap script\n'" +} + +resource "aws_security_group" "internal_security_group" { + count = local.deploy_servers_condition ? 1 : 0 + vpc_id = var.vpc_id + + egress { + from_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + protocol = "tcp" + to_port = local.provided_port_condition ? var.service_port : local.encrypted_protocol_condition ? 443 : 80 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = local.encrypted_protocol_condition ? 443 : 80 + protocol = "tcp" + to_port = local.encrypted_protocol_condition ? 443 : 80 + cidr_blocks = ["0.0.0.0/0"] + } + ingress { + from_port = -1 + protocol = "icmp" + to_port = -1 + cidr_blocks = ["0.0.0.0/0"] + } +} + +module "internal_load_balancer" { + count = local.deploy_servers_condition ? 1 : 0 + source = "../modules/common/load_balancer" + + load_balancers_type = var.load_balancers_type + instances_subnets = var.servers_subnets + prefix_name = "${var.prefix}-Internal" + internal = true + security_groups = local.alb_condition ? [aws_security_group.internal_security_group[0].id] : [] + tags = { + x-chkp-management = "${var.provision_tag}-management" + x-chkp-template = "${var.provision_tag}-template" + } + vpc_id = var.vpc_id + load_balancer_protocol = var.load_balancer_protocol + target_group_port = local.encrypted_protocol_condition ? 443 : 80 + listener_port = local.encrypted_protocol_condition ? "443" : "80" + certificate_arn = local.encrypted_protocol_condition ? var.certificate : "" +} + +module "custom_autoscale" { + count = local.deploy_servers_condition ? 1 : 0 + source = "../modules/custom-autoscale" + + prefix = var.prefix + asg_name = var.asg_name + vpc_id = var.vpc_id + servers_subnets = var.servers_subnets + server_ami = var.server_ami + server_name = "${var.provision_tag}-server" + servers_instance_type = var.servers_instance_type + key_name = var.key_name + servers_min_group_size = var.gateways_min_group_size + servers_max_group_size = var.gateways_max_group_size + servers_target_groups = module.internal_load_balancer[0].target_group_id + deploy_internal_security_group = local.nlb_condition ? true : false + source_security_group = local.nlb_condition ? "" : aws_security_group.internal_security_group[0].id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/qs-autoscale/output.tf b/deprecated/terraform/aws/R81/qs-autoscale/output.tf new file mode 100755 index 00000000..edb1a1f6 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale/output.tf @@ -0,0 +1,45 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} + +output "management_name" { + value = "${var.provision_tag}-management" +} +output "internal_port" { + value = local.encrypted_protocol_condition ? 443 : 80 +} +output "load_balancer_url" { + value = module.external_load_balancer.load_balancer_url +} +output "external_load_balancer_arn" { + value = module.external_load_balancer.load_balancer_arn +} +output "internal_load_balancer_arn" { + value = module.internal_load_balancer[*].load_balancer_arn +} +output "external_lb_target_group_arn" { + value = module.external_load_balancer.target_group_arn +} +output "internal_lb_target_group_arn" { + value = module.internal_load_balancer[*].target_group_arn +} + +output "autoscale_autoscaling_group_name" { + value = module.autoscale.autoscale_autoscaling_group_name +} +output "autoscale_autoscaling_group_arn" { + value = module.autoscale.autoscale_autoscaling_group_arn +} +output "autoscale_security_group_id" { + value = module.autoscale.autoscale_security_group_id +} +output "autoscale_iam_role_name" { + value = module.autoscale.autoscale_iam_role_name +} + +output "configuration_template" { + value = "${var.provision_tag}-template" +} +output "controller_name" { + value = "${var.provision_tag}-controller" +} diff --git a/deprecated/terraform/aws/R81/qs-autoscale/terraform.tfvars b/deprecated/terraform/aws/R81/qs-autoscale/terraform.tfvars new file mode 100755 index 00000000..d9eb16f4 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale/terraform.tfvars @@ -0,0 +1,48 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Environment --- +prefix = "TF" +asg_name = "asg-qs" + +// --- General Settings --- +vpc_id = "vpc-12345678" +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +provision_tag = "quickstart" +load_balancers_type = "Application Load Balancer" +load_balancer_protocol = "HTTP" +certificate = "" +service_port = "80" +admin_shell = "/etc/cli.sh" + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Web Servers Auto Scaling Group Configuration --- +servers_deploy = false +servers_subnets = ["subnet-1234abcd", "subnet-56789def"] +servers_instance_type = "t3.micro" +server_ami = "ami-12345678" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/qs-autoscale/variables.tf b/deprecated/terraform/aws/R81/qs-autoscale/variables.tf new file mode 100755 index 00000000..070ec4f4 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale/variables.tf @@ -0,0 +1,231 @@ +// Module: Check Point CloudGuard Network Quick Start Auto Scaling +//Deploy a Check Point CloudGuard Network Security Gateways Auto Scaling Group, an external ALB/NLB, and optionally a Security Management Server and a web server Auto Scaling Group. + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Environment --- +variable "prefix" { + type = string + description = "(Optional) Instances name prefix" + default = "" +} +variable "asg_name" { + type = string + description = "Autoscaling Group name" + default = "Check-Point-ASG-tf" +} +// --- General Settings --- +variable "vpc_id" { + type = string +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "provision_tag" { + type = string + description = "The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment" + default = "quickstart" +} +variable "load_balancers_type" { + type = string + description = "Use Network Load Balancer if you wish to preserve the source IP address and Application Load Balancer if you wish to use content based routing" + default = "Network Load Balancer" +} +variable "load_balancer_protocol" { + type = string + description = "The protocol to use on the Load Balancer" +} +variable "certificate" { + type = string + description = "Amazon Resource Name (ARN) of an HTTPS Certificate, ignored if the selected protocol is HTTP" +} +variable "service_port" { + type = string + description = "The external Load Balancer listens to this port. Leave this field blank to use default ports: 80 for HTTP and 443 for HTTPS" +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateways_subnets" { + type = list(string) + description = "Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + +// --- Web Servers Auto Scaling Group Configuration --- +variable "servers_deploy" { + type = bool + description = "Select 'true' to deploy web servers and an internal Application Load Balancer. If you select 'false' the other parameters of this section will be ignored" + default = false +} +variable "servers_subnets" { + type = list(string) + description = "Provide at least 2 private subnet IDs in the chosen VPC, separated by commas (e.g. subnet-1234,subnet-5678,subnet-9012)" +} +variable "servers_instance_type" { + type = string + description = "The EC2 instance type for the web servers" + default = "t3.micro" +} +module "validate_servers_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "server" + instance_type = var.servers_instance_type +} +variable "server_ami" { + type = string + description = "The Amazon Machine Image ID of a preconfigured web server (e.g. ami-1234)" +} diff --git a/deprecated/terraform/aws/R81/qs-autoscale/versions.tf b/deprecated/terraform/aws/R81/qs-autoscale/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/qs-autoscale/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/standalone-master/README.md b/deprecated/terraform/aws/R81/standalone-master/README.md new file mode 100755 index 00000000..3cc1d050 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone-master/README.md @@ -0,0 +1,202 @@ +# Check Point CloudGuard Network Security Management Server & Security Gateway (Standalone) Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into a new VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation + +This solution uses the following modules: +- /terraform/aws/standalone +- /terraform/aws/modules/amis +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/standalone-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/standalone: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-module /terraform/aws/standalone: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/standalone-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + - Due to terraform limitation, the apply command is: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + >Once terraform is updated, we will update accordingly. + +- Variables are configured in /terraform/aws/standalone-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + } + private_subnets_map = { + "us-east-1a" = 2 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + standalone_name = "Check-Point-Standalone-tf" + standalone_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + standalone_version = "R81.BYOL" + admin_shell = "/etc/cli.sh" + standalone_password_hash = "" + standalone_maintenance_mode_password_hash = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + standalone_hostname = "standalone-tf" + allow_upload_download = true + enable_cloudwatch = false + standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Standalone instance: + ``` + allocate_and_associate_eip = true + ``` + +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| standalone_name | (Optional) The name tag of the Security Gateway & Management (Standalone) instance | string | n/a | Check-Point-Standalone-tf | no | +| standalone_instance_type | The instance type of the Security Gateway & Management (Standalone) instance | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance | map(string) | n/a | {} | no | +| standalone_version | Security Gateway & Management (Standalone) version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R82-BYOL
- R82-PAYG-NGTP | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| standalone_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| standalone_hostname | (Optional) Security Gateway & Management (Standalone) prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| standalone_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| standalone_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|------------------------------|------------------------------------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| internal_rtb_id | The internal route table id | +| vpc_public_subnets_ids_list | A list of the public subnets ids | +| vpc_private_subnets_ids_list | A list of the private subnets ids | +| standalone_instance_id | The deployed Security Gateway & Management (Standalone) AWS instance id | +| standalone_instance_name | The deployed Security Gateway & Management (Standalone) AWS instance name | +| standalone_public_ip | The deployed Security Gateway & Management (Standalone) AWS public address | +| standalone_ssh | SSH command to the Security Gateway & Management (Standalone) | +| standalone_url | URL to the portal of the deployed Security Gateway & Management (Standalone) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231113 | Add support for BYOL license type for Standalone | +| 20231012 | Update AWS Terraform Provider version to 5.20.1 | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone-master/locals.tf b/deprecated/terraform/aws/R81/standalone-master/locals.tf new file mode 100755 index 00000000..61326301 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone-master/locals.tf @@ -0,0 +1,36 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_standalone_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.standalone_password_hash is invalid + regex_standalone_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_password_hash) == var.standalone_password_hash ? 0 : "Variable [standalone_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_maintenance_mode_password_hash) == var.standalone_maintenance_mode_password_hash ? 0 : "Variable [standalone_maintenance_mode_password_hash] must be a valid password hash" + +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone-master/main.tf b/deprecated/terraform/aws/R81/standalone-master/main.tf new file mode 100755 index 00000000..999c506e --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone-master/main.tf @@ -0,0 +1,63 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + subnets_bit_length = var.subnets_bit_length +} + +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnets" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} + +module "launch_standalone_into_vpc" { + source = "../standalone" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_id = module.launch_vpc.public_subnets_ids_list[0] + private_subnet_id = module.launch_vpc.private_subnets_ids_list[0] + private_route_table = aws_route_table.private_subnet_rtb.id + resources_tag_name = var.resources_tag_name + standalone_name = var.standalone_name + standalone_instance_type = var.standalone_instance_type + key_name = var.key_name + allocate_and_associate_eip = var.allocate_and_associate_eip + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + standalone_version = var.standalone_version + admin_shell = var.admin_shell + standalone_password_hash = var.standalone_password_hash + standalone_maintenance_mode_password_hash = var.standalone_maintenance_mode_password_hash + standalone_hostname = var.standalone_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + standalone_bootstrap_script = var.standalone_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + admin_cidr = var.admin_cidr + gateway_addresses = var.gateway_addresses +} diff --git a/deprecated/terraform/aws/R81/standalone-master/output.tf b/deprecated/terraform/aws/R81/standalone-master/output.tf new file mode 100755 index 00000000..11d557b9 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone-master/output.tf @@ -0,0 +1,27 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "internal_rtb_id" { + value = aws_route_table.private_subnet_rtb.id +} +output "vpc_public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "vpc_private_subnets_ids_list" { + value = module.launch_vpc.private_subnets_ids_list +} +output "standalone_instance_id" { + value = module.launch_standalone_into_vpc.standalone_instance_id +} +output "standalone_instance_name" { + value = module.launch_standalone_into_vpc.standalone_instance_name +} +output "standalone_public_ip" { + value = module.launch_standalone_into_vpc.standalone_public_ip +} +output "standalone_ssh" { + value = module.launch_standalone_into_vpc.standalone_ssh +} +output "standalone_url" { + value = module.launch_standalone_into_vpc.standalone_url +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone-master/terraform.tfvars b/deprecated/terraform/aws/R81/standalone-master/terraform.tfvars new file mode 100755 index 00000000..4f6b6131 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone-master/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 +} +private_subnets_map = { + "us-east-1a" = 2 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +standalone_name = "Check-Point-Standalone-tf" +standalone_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +standalone_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +standalone_password_hash = "" +standalone_maintenance_mode_password_hash = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +standalone_hostname = "standalone-tf" +allow_upload_download = true +enable_cloudwatch = false +standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone-master/variables.tf b/deprecated/terraform/aws/R81/standalone-master/variables.tf new file mode 100755 index 00000000..212dc108 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone-master/variables.tf @@ -0,0 +1,174 @@ +// Module: Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " + +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- EC2 Instance Configuration --- +variable "standalone_name" { + type = string + description = "(Optional) The name tag of the Security Gateway & Management (Standalone) instance" + default = "Check-Point-Standalone-tf" +} +variable "standalone_instance_type" { + type = string + description = "The instance type of the Security Gateway & Management (Standalone) instance" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "standalone" + instance_type = var.standalone_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "standalone_version" { + type = string + description = "Gateway & Management (Standalone) version and license" + default = "R81.20-BYOL" +} +module "validate_standalone_version" { + source = "../modules/common/version_license" + + chkp_type = "standalone" + version_license = var.standalone_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "standalone_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "standalone_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) The name tag of the resources" + default = "" +} +variable "standalone_hostname" { + type = string + description = "(Optional) Security Gateway & Management (Standalone) prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "standalone_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} diff --git a/deprecated/terraform/aws/R81/standalone-master/versions.tf b/deprecated/terraform/aws/R81/standalone-master/versions.tf new file mode 100755 index 00000000..a95f0172 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone-master/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone/README.md b/deprecated/terraform/aws/R81/standalone/README.md new file mode 100755 index 00000000..0a0562f4 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/README.md @@ -0,0 +1,178 @@ +# Check Point CloudGuard Network Security Management Server & Security Gateway (Standalone) Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) - conditional creation +* [Route](https://www.terraform.io/docs/providers/aws/r/route.html) - conditional creation + + +This solution uses the following modules: +- /terraform/aws/modules/amis + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/standalone/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/standalone/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/standalone/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + public_subnet_id = "subnet-123456" + private_subnet_id = "subnet-345678" + private_route_table = "rtb-12345678" + + // --- EC2 Instance Configuration --- + standalone_name = "Check-Point-Standalone-tf" + standalone_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + + // --- Check Point Settings --- + standalone_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + standalone_password_hash = "" + standalone_maintenance_mode_password_hash = "" + // --- Advanced Settings --- + resources_tag_name = "tag-name" + standalone_hostname = "standalone-tf" + allow_upload_download = true + enable_cloudwatch = false + standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + admin_cidr = "0.0.0.0/0" + gateway_addresses = "0.0.0.0/0" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to the Standalone instance: + ``` + allocate_and_associate_eip = true + ``` + - To create route from '0.0.0.0/0' to the Standalone instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the Security Gateway & Management (Standalone) | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the Security Gateway & Management (Standalone) | string | n/a | n/a | yes | +| private_route_table | Sets '0.0.0.0/0' route to the Security Gateway & Management (Standalone) instance in the specified route table (e.g. rtb-12a34567) | string | n/a | "" | no | +| standalone_name | (Optional) The name tag of the Security Gateway & Management (Standalone) instance | string | n/a | Check-Point-Standalone-tf | no | +| standalone_instance_type | The instance type of the Security Gateway & Management (Standalone) instance | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with the launched instance | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance | map(string) | n/a | {} | no | +| standalone_version | Security Gateway & Management (Standalone) version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R82-BYOL
- R82-PAYG-NGTP | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| standalone_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| resources_tag_name | (optional) | string | n/a | "" | no | +| standalone_hostname | (Optional) Security Gateway & Management (Standalone) prompt hostname. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| standalone_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | n/a | 0.0.0.0/0 | no | +| standalone_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|------------------------------------------------------------------------------| +| standalone_instance_id | The deployed Security Gateway & Management (Standalone) AWS instance id | +| standalone_instance_name | The deployed Security Gateway & Management (Standalone) AWS instance name | +| standalone_public_ip | The deployed Security Gateway & Management (Standalone) AWS public address | +| standalone_ssh | SSH command to the Security Gateway & Management (Standalone) | +| standalone_url | URL to the portal of the deployed Security Gateway & Management (Standalone) | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231113 | Add support for BYOL license type for Standalone | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | Stability fixes | +| 20210309 | First release of Check Point Security Management Server & Security Gateway (Standalone) Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone/locals.tf b/deprecated/terraform/aws/R81/standalone/locals.tf new file mode 100755 index 00000000..6e438e83 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/locals.tf @@ -0,0 +1,41 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + enable_cloudwatch_policy = var.enable_cloudwatch ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_cidr_range = "^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[0-2]|2[0-9]|1[0-9]|[0-9]))?$" + // Will fail if var.admin_subnet or var.gateway_addresses are invalid + mgmt_subnet_regex_result = regex(local.regex_valid_cidr_range, var.admin_cidr) == var.admin_cidr ? 0 : "var.admin_subnet must be a valid CIDR range" + gw_addr_regex_result = regex(local.regex_valid_cidr_range, var.gateway_addresses) == var.gateway_addresses ? 0 : "var.gateway_addresses must be a valid CIDR range" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + regex_valid_standalone_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.standalone_password_hash is invalid + regex_standalone_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_password_hash) == var.standalone_password_hash ? 0 : "Variable [standalone_password_hash] must be a valid password hash" + regex_maintenance_mode_password_hash = regex(local.regex_valid_standalone_password_hash, var.standalone_maintenance_mode_password_hash) == var.standalone_maintenance_mode_password_hash ? 0 : "Variable [standalone_maintenance_mode_password_hash] must be a valid password hash" + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.standalone_version), 0) + + standalone_bootstrap_script64 = base64encode(var.standalone_bootstrap_script) + standalone_password_hash_base64 = base64encode(var.standalone_password_hash) + maintenance_mode_password_hash_base64 = base64encode(var.standalone_maintenance_mode_password_hash) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone/main.tf b/deprecated/terraform/aws/R81/standalone/main.tf new file mode 100755 index 00000000..f9df43ff --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/main.tf @@ -0,0 +1,145 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "amis" { + source = "../modules/amis" + + version_license = var.standalone_version + chkp_type = "standalone" +} + +module "common_permissive_sg" { + source = "../modules/common/permissive_sg" + + vpc_id = var.vpc_id + resources_tag_name = var.resources_tag_name + gateway_name = var.standalone_name +} + +resource "aws_iam_instance_profile" "standalone_instance_profile" { + count = local.enable_cloudwatch_policy + path = "/" + role = aws_iam_role.standalone_iam_role[count.index].name +} + +resource "aws_iam_role" "standalone_iam_role" { + count = local.enable_cloudwatch_policy + assume_role_policy = data.aws_iam_policy_document.standalone_role_assume_policy_document.json + path = "/" +} + +data "aws_iam_policy_document" "standalone_role_assume_policy_document" { + version = "2012-10-17" + statement { + effect = "Allow" + actions = ["sts:AssumeRole"] + principals { + type = "Service" + identifiers = ["ec2.amazonaws.com"] + } + } +} + +module "attach_cloudwatch_policy" { + source = "../modules/cloudwatch-policy" + count = local.enable_cloudwatch_policy + role = aws_iam_role.standalone_iam_role[count.index].name + tag_name = var.resources_tag_name != "" ? var.resources_tag_name : var.standalone_name +} +resource "aws_network_interface" "public_eni" { + subnet_id = var.public_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth0" + source_dest_check = false + tags = { + Name = format("%s-external-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.standalone_name) } +} +resource "aws_network_interface" "private_eni" { + subnet_id = var.private_subnet_id + security_groups = [module.common_permissive_sg.permissive_sg_id] + description = "eth1" + source_dest_check = false + tags = { + Name = format("%s-internal-eni", var.resources_tag_name != "" ? var.resources_tag_name : var.standalone_name) } +} + +module "common_eip" { + source = "../modules/common/elastic_ip" + + allocate_and_associate_eip = var.allocate_and_associate_eip + external_eni_id = aws_network_interface.public_eni.id + private_ip_address = aws_network_interface.public_eni.private_ip +} + +module "common_internal_default_route" { + source = "../modules/common/internal_default_route" + + private_route_table = var.private_route_table + internal_eni_id = aws_network_interface.private_eni.id +} + +resource "aws_launch_template" "standalone_launch_template" { + instance_type = var.standalone_instance_type + key_name = var.key_name + image_id = module.amis.ami_id + description = "Initial launch template version" + + iam_instance_profile { + name = (local.enable_cloudwatch_policy == 1 ? aws_iam_instance_profile.standalone_instance_profile[0].id : "") + } + + network_interfaces { + network_interface_id = aws_network_interface.public_eni.id + device_index = 0 + } + + metadata_options { + http_tokens = var.metadata_imdsv2_required ? "required" : "optional" + } + + network_interfaces { + network_interface_id = aws_network_interface.private_eni.id + device_index = 1 + } +} + +resource "aws_instance" "standalone-instance" { + launch_template { + id = aws_launch_template.standalone_launch_template.id + version = "$Latest" + } + + disable_api_termination = var.disable_instance_termination + + tags = merge({ + Name = var.standalone_name + }, var.instance_tags) + + ebs_block_device { + device_name = "/dev/xvda" + volume_type = "gp2" + volume_size = var.volume_size + encrypted = local.volume_encryption_condition + kms_key_id = local.volume_encryption_condition ? var.volume_encryption : "" + } + + user_data = templatefile("${path.module}/standalone_userdata.yaml", { + // script's arguments + Hostname = var.standalone_hostname, + PasswordHash = local.standalone_password_hash_base64, + MaintenanceModePassword = local.maintenance_mode_password_hash_base64, + AllowUploadDownload = var.allow_upload_download, + EnableCloudWatch = var.enable_cloudwatch, + NTPPrimary = var.primary_ntp, + NTPSecondary = var.secondary_ntp, + Shell = var.admin_shell, + AdminSubnet = var.admin_cidr, + EnableInstanceConnect = var.enable_instance_connect, + StandaloneBootstrapScript = local.standalone_bootstrap_script64 + AllocateElasticIP = var.allocate_and_associate_eip + OsVersion = local.version_split + }) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone/output.tf b/deprecated/terraform/aws/R81/standalone/output.tf new file mode 100755 index 00000000..5a46d0fa --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/output.tf @@ -0,0 +1,15 @@ +output "standalone_instance_id" { + value = aws_instance.standalone-instance.id +} +output "standalone_instance_name" { + value = aws_instance.standalone-instance.tags["Name"] +} +output "standalone_public_ip" { + value = aws_instance.standalone-instance.public_ip +} +output "standalone_ssh" { + value = format("ssh -i %s admin@%s", var.key_name, aws_instance.standalone-instance.public_ip) +} +output "standalone_url" { + value = format("https://%s", aws_instance.standalone-instance.public_ip) +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone/standalone_userdata.yaml b/deprecated/terraform/aws/R81/standalone/standalone_userdata.yaml new file mode 100755 index 00000000..0bf47ec4 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/standalone_userdata.yaml @@ -0,0 +1,4 @@ +#cloud-config +runcmd: + - | + python3 /etc/cloud_config.py enableCloudWatch=\"${EnableCloudWatch}\" installationType=\"standalone\" osVersion=\"${OsVersion}\" allowUploadDownload=\"${AllowUploadDownload}\" templateVersion=\"20240704\" templateName=\"standalone\" templateType=\"terraform\" shell=\"${Shell}\" enableInstanceConnect=\"${EnableInstanceConnect}\" hostName=\"${Hostname }\" ntpPrimary=\"${NTPPrimary}\" ntpSecondary=\"${NTPSecondary}\" passwordHash=\"${PasswordHash}\" MaintenanceModePassword=\"${MaintenanceModePassword}\" adminSubnet=\"${AdminSubnet}\" allocatePublicAddress=\"${AllocateElasticIP}\" bootstrapScript64=\"${StandaloneBootstrapScript}\" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone/terraform.tfvars b/deprecated/terraform/aws/R81/standalone/terraform.tfvars new file mode 100755 index 00000000..edad70cd --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/terraform.tfvars @@ -0,0 +1,39 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +public_subnet_id = "subnet-123456" +private_subnet_id = "subnet-345678" +private_route_table = "rtb-12345678" + +// --- EC2 Instance Configuration --- +standalone_name = "Check-Point-Standalone-tf" +standalone_instance_type = "c5.xlarge" +key_name = "publickey" +allocate_and_associate_eip = true +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +instance_tags = { + key1 = "value1" + key2 = "value2" +} + +// --- Check Point Settings --- +standalone_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +standalone_password_hash = "" +standalone_maintenance_mode_password_hash = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +standalone_hostname = "standalone-tf" +allow_upload_download = true +enable_cloudwatch = false +standalone_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" +admin_cidr = "0.0.0.0/0" +gateway_addresses = "0.0.0.0/0" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/standalone/variables.tf b/deprecated/terraform/aws/R81/standalone/variables.tf new file mode 100755 index 00000000..afdec993 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/variables.tf @@ -0,0 +1,172 @@ +// Module: Check Point CloudGuard Network Security Gateway & Management (Standalone) instance into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_id" { + type = string + description = "The public subnet of the Security Gateway & Management (Standalone)" +} +variable "private_subnet_id" { + type = string + description = "The private subnet of the Security Gateway & Management (Standalone)" +} +variable "private_route_table" { + type = string + description = "Sets '0.0.0.0/0' route to the Security Gateway & Management (Standalone) instance in the specified route table (e.g. rtb-12a34567)" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "standalone_name" { + type = string + description = "(Optional) The name tag of the Security Gateway & Management (Standalone) instance" + default = "Check-Point-Standalone-tf" +} +variable "standalone_instance_type" { + type = string + description = "The instance type of the Security Gateway & Management (Standalone) instance" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "standalone" + instance_type = var.standalone_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with the launched instance" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Standalone EC2 Instance" + default = {} +} + +// --- Check Point Settings --- +variable "standalone_version" { + type = string + description = "Security Gateway & Management (Standalone) version and license" + default = "R81.20-BYOL" +} +module "validate_standalone_version" { + source = "../modules/common/version_license" + + chkp_type = "standalone" + version_license = var.standalone_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "standalone_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "standalone_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) The name tag of the resources" + default = "" +} +variable "standalone_hostname" { + type = string + description = "(Optional) Security Gateway & Management (Standalone) prompt hostname" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "standalone_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} +variable "admin_cidr" { + type = string + description = "(CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} +variable "gateway_addresses" { + type = string + description = "(CIDR) Allow gateways only from this network to communicate with the Management Server" + default = "0.0.0.0/0" +} diff --git a/deprecated/terraform/aws/R81/standalone/versions.tf b/deprecated/terraform/aws/R81/standalone/versions.tf new file mode 100755 index 00000000..c138bbb3 --- /dev/null +++ b/deprecated/terraform/aws/R81/standalone/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + } +} diff --git a/deprecated/terraform/aws/R81/tests/cluster_master_test.go b/deprecated/terraform/aws/R81/tests/cluster_master_test.go new file mode 100755 index 00000000..adf31fe9 --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/cluster_master_test.go @@ -0,0 +1,100 @@ +package tests + +import ( + "github.com/stretchr/testify/assert" + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" +) + +// Test the Terraform module in aws/cluster-master using terratest. +func TestClusterMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsClusterMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetClusterMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsClusterMaster(t, terraformOptions) +} + +func GetTerraformOptionsClusterMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../cluster-master", + + // Variables passed to the module execution using -var options. To change any value refer to globals.go + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMapSingle, + "private_subnets_map": privateSubnetsMapSingle, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": clusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "allocate_and_associate_eip": allocateAndAssociatePublicEip, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueClusterGateway}, + "predefined_role": predefinedRole, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "memberAToken": gatewaySmart1CloudToken, + "memberBToken": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetClusterMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsClusterMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsClusterMaster(t *testing.T, terraformOptions *terraform.Options) { + outputAmiId := terraform.Output(t, terraformOptions, "ami_id") + outputClusterPublicIP := terraform.Output(t, terraformOptions, "cluster_public_ip") + outputMemberAEipPublicIP := terraform.Output(t, terraformOptions, "member_a_public_ip") + outputMemberBEipPublicIP := terraform.Output(t, terraformOptions, "member_b_public_ip") + outputMemberASSH := terraform.Output(t, terraformOptions, "member_a_ssh") + outputMemberBSSH := terraform.Output(t, terraformOptions, "member_b_ssh") + outputMemberAURL := terraform.Output(t, terraformOptions, "member_a_url") + outputMemberBURL := terraform.Output(t, terraformOptions, "member_b_url") + + assert.NotEmpty(t, outputAmiId) + assert.NotEmpty(t, outputClusterPublicIP) + assert.NotEmpty(t, outputMemberAEipPublicIP) + assert.NotEmpty(t, outputMemberBEipPublicIP) + assert.NotEmpty(t, outputMemberASSH) + assert.NotEmpty(t, outputMemberBSSH) + assert.NotEmpty(t, outputMemberAURL) + assert.NotEmpty(t, outputMemberBURL) +} diff --git a/deprecated/terraform/aws/R81/tests/cross_az_cluster_master_test.go b/deprecated/terraform/aws/R81/tests/cross_az_cluster_master_test.go new file mode 100755 index 00000000..9e09bcef --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/cross_az_cluster_master_test.go @@ -0,0 +1,99 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" + "testing" +) + +// Test the Terraform module in aws/cross-az-cluster-master using terratest. +func TestCrossAzClusterMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsCrossAzClusterMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetCrossAzClusterMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsCrossAzClusterMaster(t, terraformOptions) +} + +func GetTerraformOptionsCrossAzClusterMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../cross-az-cluster-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "private_subnets_map": privateSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": crossAZClusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueClusterGateway}, + "predefined_role": predefinedRole, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "memberAToken": gatewaySmart1CloudToken, + "memberBToken": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetCrossAzClusterMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsCrossAzClusterMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsCrossAzClusterMaster(t *testing.T, terraformOptions *terraform.Options) { + outputAmiId := terraform.Output(t, terraformOptions, "ami_id") + outputClusterPublicIP := terraform.Output(t, terraformOptions, "cluster_public_ip") + outputMemberAPublicIP := terraform.Output(t, terraformOptions, "member_a_public_ip") + outputMemberBPublicIP := terraform.Output(t, terraformOptions, "member_b_public_ip") + outputMemberASSH := terraform.Output(t, terraformOptions, "member_a_ssh") + outputMemberBSSH := terraform.Output(t, terraformOptions, "member_b_ssh") + outputMemberAURL := terraform.Output(t, terraformOptions, "member_a_url") + outputMemberBURL := terraform.Output(t, terraformOptions, "member_b_url") + + // Validate that all output values exist + assert.NotEmpty(t, outputAmiId) + assert.NotEmpty(t, outputClusterPublicIP) + assert.NotEmpty(t, outputMemberAPublicIP) + assert.NotEmpty(t, outputMemberASSH) + assert.NotEmpty(t, outputMemberAURL) + assert.NotEmpty(t, outputMemberBPublicIP) + assert.NotEmpty(t, outputMemberBSSH) + assert.NotEmpty(t, outputMemberBURL) +} diff --git a/deprecated/terraform/aws/R81/tests/gateway_master_test.go b/deprecated/terraform/aws/R81/tests/gateway_master_test.go new file mode 100755 index 00000000..dd803d59 --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/gateway_master_test.go @@ -0,0 +1,119 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/aws" + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/gateway-master using terratest. +func TestGatewayMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsGatewayMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetGatewayMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsGatewayMaster(t, terraformOptions) +} + +func GetTerraformOptionsGatewayMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../gateway-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMapSingle, + "private_subnets_map": privateSubnetsMapSingle, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": gatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "allocate_and_associate_eip": allocateAndAssociatePublicEip, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueGateway}, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "gateway_TokenKey": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + + "control_gateway_over_public_or_private_address": gatewaysProvisionAddressType, + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetGatewayMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsGatewayMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsGatewayMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputInternalRouteTableId := terraform.Output(t, terraformOptions, "internal_rtb_id") + outputVpcPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_public_subnets_ids_list") + outputVpcPrivateSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_private_subnets_ids_list") + outputAmiId := terraform.Output(t, terraformOptions, "ami_id") + outputPermissiveSgId := terraform.Output(t, terraformOptions, "permissive_sg_id") + outputPermissiveSgName := terraform.Output(t, terraformOptions, "permissive_sg_name") + outputGatewayUrl := terraform.Output(t, terraformOptions, "gateway_url") + outputGatewayPublicIp := terraform.Output(t, terraformOptions, "gateway_public_ip") + outputGatewayInstanceId := terraform.Output(t, terraformOptions, "gateway_instance_id") + outputGatewayInstanceName := terraform.Output(t, terraformOptions, "gateway_instance_name") + + instanceTags := aws.GetTagsForEc2Instance(t, region, outputGatewayInstanceId) + nameTag, containsNameTag := instanceTags["Name"] + assert.True(t, containsNameTag) + assert.Equal(t, gatewayExpectedName, nameTag) + assert.Equal(t, gatewayExpectedName, outputGatewayInstanceName) + + testTag, containsTestTag := instanceTags[expectedTestTagKey] + assert.True(t, containsTestTag) + assert.Equal(t, expectedTestTagValueGateway, testTag) + + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputInternalRouteTableId) + assert.NotEmpty(t, outputVpcPublicSubnetsIdsList) + assert.NotEmpty(t, outputVpcPrivateSubnetsIdsList) + assert.NotEmpty(t, outputAmiId) + assert.NotEmpty(t, outputPermissiveSgId) + assert.NotEmpty(t, outputPermissiveSgName) + assert.NotEmpty(t, outputGatewayUrl) + assert.NotEmpty(t, outputGatewayPublicIp) + assert.NotEmpty(t, outputGatewayInstanceId) + assert.NotEmpty(t, outputGatewayInstanceName) +} diff --git a/deprecated/terraform/aws/R81/tests/globals.go b/deprecated/terraform/aws/R81/tests/globals.go new file mode 100755 index 00000000..647a026f --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/globals.go @@ -0,0 +1,177 @@ +package tests + +import "fmt" + +// AWS region for deployed resources +const region = "ca-central-1" + +var envVars = map[string]string{ + "AWS_DEFAULT_REGION": region, +} + +const availabilityZoneA = region + "a" + +const availabilityZoneB = region + "b" + +// Predefined prefix for deployed resources +const predefinedPrefix = "test" + +// Predefined names for deployed resources +const gatewayPredefinedName = "CheckPoint-Gateway" + +const standalonePredefinedName = "CheckPoint-Standalone" + +const managementPredefinedName = "CheckPoint-Management" + +const gwlbPredefinedName = "CheckPoint-GWLB" + +const clusterGatewayPredefinedName = "CheckPoint-Cluster-Gateway" + +const crossAZClusterGatewayPredefinedName = "CheckPoint-Cross-AZ-Cluster-Gateway" + +const qsAutoscaleGatewayPredefinedName = "quickstart-security-gateway" + +const qsAutoscaleProvisionTag = "quickstart" + +const configurationTemplate = "configuration-template" + +// Expected names for deployed resources +func getExpectedName(predefinedName string) string { + return fmt.Sprintf("%s-%s", predefinedPrefix, predefinedName) +} + +var gatewayExpectedName = getExpectedName(gatewayPredefinedName) + +var standaloneExpectedName = getExpectedName(standalonePredefinedName) + +var managementExpectedName = getExpectedName(managementPredefinedName) + +var gwlbExpectedName = getExpectedName(gwlbPredefinedName) + +var clusterGatewayExpectedName = getExpectedName(clusterGatewayPredefinedName) + +var crossAZClusterGatewayExpectedName = getExpectedName(crossAZClusterGatewayPredefinedName) + +var qsAutoscaleGatewayExpectedName = getExpectedName(qsAutoscaleGatewayPredefinedName) + +// Autoscale group capacity configuration +const autoscaleGroupExpectedCapacityMin = 1 + +const autoscaleGroupExpectedCapacityMax = 1 + +const targetGroup1Name = "tf-test-target-group-1" + +// Common parameters for deployed resources +const keyName = "tf-test" + +const version = "R81.20-BYOL" + +const standaloneVersion = "R81.20-BYOL" + +const adminShell = "/bin/bash" + +const gatewayBootstrapScript = "echo 'this is gateway bootstrap script' > /home/admin/bootstrap.txt" + +const standaloneBootstrapScript = "echo 'this is standalone bootstrap script' > /home/admin/bootstrap.txt" + +const passwordHash = "12345678" + +const SICKey = "12345678" + +const gatewayInstanceType = "c5.xlarge" + +const standaloneInstanceType = gatewayInstanceType + +const managementInstanceType = "m5.xlarge" + +const volumeSize = 100 + +const volumeEncryption = "alias/aws/ebs" + +const webServerInstanceType = "t3.micro" + +const webServerAMI = "ami-0718a739967397e7d" + +const volumeType = "gp3" + +const anywhereAddress = "0.0.0.0/0" + +const loadBalancersType = "Network Load Balancer" + +const loadBalancerProtocol = "TCP" + +const certificate = "" + +const servicePort = "80" + +const enableVolumeEncryption = true + +const allocatePublicIP = true + +const allocateAndAssociatePublicEip = true + +const allowUploadDownload = true + +const enableInstanceConnect = true + +const enableCloudWatch = false + +const connectionAcceptanceRequired = false + +const enableCrossZoneLoadBalancing = true + +const managementDeploy = true + +const webServerDeploy = true + +const gatewaysBlades = true + +const disableInstanceTermination = false + +const gatewaySmart1CloudToken = "" + +const predefinedRole = "" + +const primaryNtp = "" + +const secondaryNtp = "" + +const expectedTestTagKey = "test_tag" + +const expectedTestTagValueClusterGateway = "cluster_gateway_tf" + +const expectedTestTagValueGateway = "gateway_tf" + +const autoscaleGroupName = "CheckPoint-ASG" + +const resourcesTagName = "tag-name" + +const gatewayHostname = "gw-hostname" + +const gatewaysProvisionAddressType = "private" + +const gatewaysPolicy = "Standard" + +const gatewayManagement = "Locally managed" + +// New VPC configuration +const vpcCIDR = "10.0.0.0/16" + +var publicSubnetsMap = map[string]int{availabilityZoneA: 1, availabilityZoneB: 3} + +var privateSubnetsMap = map[string]int{availabilityZoneA: 2, availabilityZoneB: 4} + +var publicSubnetsMapSingle = map[string]int{availabilityZoneA: 1} + +var privateSubnetsMapSingle = map[string]int{availabilityZoneA: 2} + +var tgwSubnetsMap = map[string]int{availabilityZoneA: 5, availabilityZoneB: 6} + +var availabilityZones = []string{availabilityZoneA, availabilityZoneB} + +const numberOfAZs = 2 + +const subnetsBitLength = 8 + +// Controller expected names +const gwlbControlllerExpectedName = "gwlb-controller" diff --git a/deprecated/terraform/aws/R81/tests/gwlb_master_test.go b/deprecated/terraform/aws/R81/tests/gwlb_master_test.go new file mode 100755 index 00000000..787277a8 --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/gwlb_master_test.go @@ -0,0 +1,99 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/gwlb-master using terratest. +func TestGwlbMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsGwlbMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsGwlbMaster(t, terraformOptions) +} + +func GetTerraformOptionsGwlbMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../gwlb-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "volume_size": volumeSize, + "enable_instance_connect": enableInstanceConnect, + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + "admin_shell": adminShell, + + "gateway_load_balancer_name": gwlbExpectedName, + "target_group_name": targetGroup1Name, + "connection_acceptance_required": connectionAcceptanceRequired, + "enable_cross_zone_load_balancing": enableCrossZoneLoadBalancing, + + "gateway_name": gatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "minimum_group_size": autoscaleGroupExpectedCapacityMin, + "maximum_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "gateways_provision_address_type": gatewaysProvisionAddressType, + "allocate_public_IP": allocatePublicIP, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "gateways_policy": gatewaysPolicy, + "gateway_management": gatewayManagement, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + + "volume_type": volumeType, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsGwlbMaster(t *testing.T, terraformOptions *terraform.Options) { + outputDeployment := terraform.Output(t, terraformOptions, "Deployment") + outputManagementPublicIP := terraform.Output(t, terraformOptions, "management_public_ip") + outputGWLBARN := terraform.Output(t, terraformOptions, "gwlb_arn") + outputGWLBServiceName := terraform.Output(t, terraformOptions, "gwlb_service_name") + outputGWLBName := terraform.Output(t, terraformOptions, "gwlb_name") + outputGWLBControllerName := terraform.Output(t, terraformOptions, "controller_name") + outputConfigurationTemplateName := terraform.Output(t, terraformOptions, "template_name") + + assert.Equal(t, outputGWLBName, gwlbExpectedName) + assert.Equal(t, outputGWLBControllerName, gwlbControlllerExpectedName) + assert.Equal(t, outputConfigurationTemplateName, configurationTemplate) + + assert.NotEmpty(t, outputDeployment) + assert.NotEmpty(t, outputManagementPublicIP) + assert.NotEmpty(t, outputGWLBARN) + assert.NotEmpty(t, outputGWLBServiceName) +} diff --git a/deprecated/terraform/aws/R81/tests/qs_autoscale_master_test.go b/deprecated/terraform/aws/R81/tests/qs_autoscale_master_test.go new file mode 100755 index 00000000..df2bdbab --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/qs_autoscale_master_test.go @@ -0,0 +1,129 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/aws" + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in qs-autoscale-master using terratest. +func TestQsAutoscaleMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsQsAutoscaleMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsQsAutoscaleMaster(t, terraformOptions) +} + +func GetTerraformOptionsQsAutoscaleMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../qs-autoscale-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "prefix": predefinedPrefix, + "asg_name": autoscaleGroupName, + + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "private_subnets_map": privateSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "allow_upload_download": allowUploadDownload, + "provision_tag": qsAutoscaleProvisionTag, + + "load_balancers_type": loadBalancersType, + "load_balancer_protocol": loadBalancerProtocol, + "certificate": certificate, + "service_port": servicePort, + + "gateway_instance_type": gatewayInstanceType, + "gateways_min_group_size": autoscaleGroupExpectedCapacityMin, + "gateways_max_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "enable_cloudwatch": enableCloudWatch, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "gateways_policy": gatewaysPolicy, + "gateways_blades": gatewaysBlades, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + + "servers_deploy": webServerDeploy, + "servers_instance_type": webServerInstanceType, + "server_ami": webServerAMI, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsQsAutoscaleMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "public_subnets_ids_list") + outputPrivateSubnetsIdsList := terraform.Output(t, terraformOptions, "private_subnets_ids_list") + outputManagementInstanceName := terraform.Output(t, terraformOptions, "management_name") + outputLBUrl := terraform.Output(t, terraformOptions, "load_balancer_url") + outputExternalLBId := terraform.Output(t, terraformOptions, "external_load_balancer_arn") + outputInternalLBId := terraform.Output(t, terraformOptions, "internal_load_balancer_arn") + outputExternalTGId := terraform.Output(t, terraformOptions, "external_lb_target_group_arn") + outputInternalTGId := terraform.Output(t, terraformOptions, "internal_lb_target_group_arn") + outputGwsASGId := terraform.Output(t, terraformOptions, "autoscale_autoscaling_group_arn") + outputSecurityGroup := terraform.Output(t, terraformOptions, "autoscale_security_group_id") + + asgName := terraform.Output(t, terraformOptions, "autoscale_autoscaling_group_name") + asgCapacityInfo := aws.GetCapacityInfoForAsg(t, asgName, region) + awsInstancesIds := aws.GetInstanceIdsForAsg(t, asgName, region) + + // website::tag::3:: + // Verify the ASG's Gateway instances contain the expected Name tag value + for _, instanceId := range awsInstancesIds { + // Look up the tags for the given Instance ID + instanceTags := aws.GetTagsForEc2Instance(t, region, instanceId) + + nameTag, containsNameTag := instanceTags["Name"] + assert.True(t, containsNameTag) + assert.Equal(t, qsAutoscaleGatewayExpectedName, nameTag) + } + + // Verify the ASG capacity info matches the expected + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMax), asgCapacityInfo.MaxCapacity) + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMin), asgCapacityInfo.MinCapacity) + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMin), asgCapacityInfo.CurrentCapacity) + assert.Equal(t, int64(autoscaleGroupExpectedCapacityMin), asgCapacityInfo.DesiredCapacity) + + assert.NotEmpty(t, outputManagementInstanceName) + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputPublicSubnetsIdsList) + assert.NotEmpty(t, outputPrivateSubnetsIdsList) + assert.NotEmpty(t, outputLBUrl) + assert.NotEmpty(t, outputExternalLBId) + assert.NotEmpty(t, outputInternalLBId) + assert.NotEmpty(t, outputExternalTGId) + assert.NotEmpty(t, outputInternalTGId) + assert.NotEmpty(t, outputGwsASGId) + assert.NotEmpty(t, outputSecurityGroup) +} diff --git a/deprecated/terraform/aws/R81/tests/standalone_master_test.go b/deprecated/terraform/aws/R81/tests/standalone_master_test.go new file mode 100755 index 00000000..c04e7f78 --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/standalone_master_test.go @@ -0,0 +1,112 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/aws" + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/standalone-master using terratest. +func TestStandaloneMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsStandaloneMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetStandaloneMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsStandaloneMaster(t, terraformOptions) +} + +func GetTerraformOptionsStandaloneMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../standalone-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMapSingle, + "private_subnets_map": privateSubnetsMapSingle, + "subnets_bit_length": subnetsBitLength, + + "standalone_name": standaloneExpectedName, + "standalone_instance_type": standaloneInstanceType, + "key_name": keyName, + "allocate_and_associate_eip": allocateAndAssociatePublicEip, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "instance_tags": map[string]string{expectedTestTagKey: expectedTestTagValueGateway}, + + "standalone_version": standaloneVersion, + "admin_shell": adminShell, + "standalone_password_hash": passwordHash, + "standalone_maintenance_mode_password_hash": passwordHash, + + "resources_tag_name": resourcesTagName, + "standalone_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "standalone_bootstrap_script": standaloneBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + "admin_cidr": anywhereAddress, + "gateway_addresses": anywhereAddress, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetStandaloneMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsStandaloneMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsStandaloneMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputInternalRouteTableId := terraform.Output(t, terraformOptions, "internal_rtb_id") + outputVpcPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_public_subnets_ids_list") + outputVpcPrivateSubnetsIdsList := terraform.Output(t, terraformOptions, "vpc_private_subnets_ids_list") + outputStandaloneInstanceId := terraform.Output(t, terraformOptions, "standalone_instance_id") + outputStandaloneInstanceName := terraform.Output(t, terraformOptions, "standalone_instance_name") + outputStandalonePublicIP := terraform.Output(t, terraformOptions, "standalone_public_ip") + outputStandaloneSSH := terraform.Output(t, terraformOptions, "standalone_ssh") + outputStandaloneURL := terraform.Output(t, terraformOptions, "standalone_url") + + // website::tag::3:: + // Verify the Standalone's instances contain the expected Name tag value + instanceTags := aws.GetTagsForEc2Instance(t, region, outputStandaloneInstanceId) + nameTag, containsNameTag := instanceTags["Name"] + assert.True(t, containsNameTag) + assert.Equal(t, standaloneExpectedName, nameTag) + assert.Equal(t, standaloneExpectedName, outputStandaloneInstanceName) + + testTag, containsTestTag := instanceTags[expectedTestTagKey] + assert.True(t, containsTestTag) + assert.Equal(t, expectedTestTagValueGateway, testTag) + + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputInternalRouteTableId) + assert.NotEmpty(t, outputVpcPublicSubnetsIdsList) + assert.NotEmpty(t, outputVpcPrivateSubnetsIdsList) + assert.NotEmpty(t, outputStandaloneInstanceId) + assert.NotEmpty(t, outputStandaloneInstanceName) + assert.NotEmpty(t, outputStandalonePublicIP) + assert.NotEmpty(t, outputStandaloneSSH) + assert.NotEmpty(t, outputStandaloneURL) +} diff --git a/deprecated/terraform/aws/R81/tests/tgw_asg_master_test.go b/deprecated/terraform/aws/R81/tests/tgw_asg_master_test.go new file mode 100755 index 00000000..c5c98afa --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/tgw_asg_master_test.go @@ -0,0 +1,95 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/tgw-asg-master using terratest. +func TestTgwAsgMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsTgwAsgMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsTgwAsgMaster(t, terraformOptions) +} + +func GetTerraformOptionsTgwAsgMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../tgw-asg-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "allow_upload_download": allowUploadDownload, + + "gateway_name": crossAZClusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "gateways_min_group_size": autoscaleGroupExpectedCapacityMin, + "gateways_max_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "enable_cloudwatch": enableCloudWatch, + "asn": 6500, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "management_permissions": "Create with read-write permissions", + "management_predefined_role": predefinedRole, + "gateways_blades": gatewaysBlades, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + "gateway_management": gatewayManagement, + + "control_gateway_over_public_or_private_address": "private", + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsTgwAsgMaster(t *testing.T, terraformOptions *terraform.Options) { + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + outputVpcPublicSubnetsIdsList := terraform.Output(t, terraformOptions, "public_subnets_ids_list") + outputManagementInstanceName := terraform.Output(t, terraformOptions, "management_instance_name") + outputConfigurationTemplate := terraform.Output(t, terraformOptions, "configuration_template") + outputControllerName := terraform.Output(t, terraformOptions, "controller_name") + outputManagementPublicIP := terraform.Output(t, terraformOptions, "management_public_ip") + outputManagementURL := terraform.Output(t, terraformOptions, "management_url") + outputAutoscalingGroupName := terraform.Output(t, terraformOptions, "autoscaling_group_name") + + assert.NotEmpty(t, outputVpcId) + assert.NotEmpty(t, outputVpcPublicSubnetsIdsList) + assert.NotEmpty(t, outputManagementInstanceName) + assert.NotEmpty(t, outputConfigurationTemplate) + assert.NotEmpty(t, outputControllerName) + assert.NotEmpty(t, outputManagementPublicIP) + assert.NotEmpty(t, outputManagementURL) + assert.NotEmpty(t, outputAutoscalingGroupName) +} diff --git a/deprecated/terraform/aws/R81/tests/tgw_cross_az_cluster_master_test.go b/deprecated/terraform/aws/R81/tests/tgw_cross_az_cluster_master_test.go new file mode 100755 index 00000000..8220bcd3 --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/tgw_cross_az_cluster_master_test.go @@ -0,0 +1,103 @@ +package tests + +import ( + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" + "testing" +) + +// Test the Terraform module in aws/tgw-cross-az-cluster-master using terratest. +func TestTgwCrossAzClusterMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsTgwCrossAzClusterMaster() + terraformOptionsWithTarget := GetTerraformOptionsWithTargetTgwCrossAzClusterMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptionsWithTarget) + terraform.Apply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsTgwCrossAzClusterMaster(t, terraformOptions) +} + +func GetTerraformOptionsTgwCrossAzClusterMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../tgw-cross-az-cluster-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "private_subnets_map": privateSubnetsMap, + "tgw_subnets_map": tgwSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "gateway_name": crossAZClusterGatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "key_name": keyName, + "volume_size": volumeSize, + "volume_encryption": volumeEncryption, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + + "predefined_role": predefinedRole, + + "gateway_version": version, + "admin_shell": adminShell, + "gateway_SICKey": SICKey, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + + "memberAToken": gatewaySmart1CloudToken, + "memberBToken": gatewaySmart1CloudToken, + + "resources_tag_name": resourcesTagName, + "gateway_hostname": gatewayHostname, + "allow_upload_download": allowUploadDownload, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + "primary_ntp": primaryNtp, + "secondary_ntp": secondaryNtp, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func GetTerraformOptionsWithTargetTgwCrossAzClusterMaster() *terraform.Options { + terraformOptionsWithTarget := GetTerraformOptionsTgwCrossAzClusterMaster() + terraformOptionsWithTarget.Targets = []string{"aws_route_table.private_subnet_rtb"} + + return terraformOptionsWithTarget +} + +func ValidateOutputsTgwCrossAzClusterMaster(t *testing.T, terraformOptions *terraform.Options) { + outputClusterPublicIP := terraform.Output(t, terraformOptions, "cluster_public_ip") + outputMemberAPublicIP := terraform.Output(t, terraformOptions, "member_a_public_ip") + outputMemberBPublicIP := terraform.Output(t, terraformOptions, "member_b_public_ip") + outputMemberASSH := terraform.Output(t, terraformOptions, "member_a_ssh") + outputMemberBSSH := terraform.Output(t, terraformOptions, "member_b_ssh") + outputMemberAURL := terraform.Output(t, terraformOptions, "member_a_url") + outputMemberBURL := terraform.Output(t, terraformOptions, "member_b_url") + outputMemberAENI := terraform.Output(t, terraformOptions, "member_a_eni") + outputMemberBENI := terraform.Output(t, terraformOptions, "member_b_eni") + outputVpcId := terraform.Output(t, terraformOptions, "vpc_id") + + assert.NotEmpty(t, outputClusterPublicIP) + assert.NotEmpty(t, outputMemberAPublicIP) + assert.NotEmpty(t, outputMemberASSH) + assert.NotEmpty(t, outputMemberAURL) + assert.NotEmpty(t, outputMemberBPublicIP) + assert.NotEmpty(t, outputMemberBSSH) + assert.NotEmpty(t, outputMemberBURL) + assert.NotEmpty(t, outputMemberAENI) + assert.NotEmpty(t, outputMemberBENI) + assert.NotEmpty(t, outputVpcId) +} diff --git a/deprecated/terraform/aws/R81/tests/tgw_gwlb_master_test.go b/deprecated/terraform/aws/R81/tests/tgw_gwlb_master_test.go new file mode 100755 index 00000000..da863cea --- /dev/null +++ b/deprecated/terraform/aws/R81/tests/tgw_gwlb_master_test.go @@ -0,0 +1,110 @@ +package tests + +import ( + "testing" + + "github.com/gruntwork-io/terratest/modules/terraform" + "github.com/stretchr/testify/assert" +) + +// Test the Terraform module in aws/tgw-gwlb-master using terratest. +func TestTgwGwlbMaster(t *testing.T) { + t.Parallel() + + // website::tag::1::Configure Terraform setting path to Terraform code, EC2 instance name, and AWS Region. + terraformOptions := GetTerraformOptionsTgwGwlbMaster() + + // website::tag::4::At the end of the tests, run `terraform destroy` to clean up any resources that were created + defer terraform.Destroy(t, terraformOptions) + + // website::tag::2::Run `terraform init` and `terraform apply` and fail the tests if there are any errors + terraform.InitAndApply(t, terraformOptions) + + // Run 'terraform output' and validate output values + ValidateOutputsTgwGwlbMaster(t, terraformOptions) +} + +func GetTerraformOptionsTgwGwlbMaster() *terraform.Options { + terraformOptions := &terraform.Options{ + TerraformDir: "../tgw-gwlb-master", + + // Variables passed to the module execution using -var options + Vars: map[string]interface{}{ + "vpc_cidr": vpcCIDR, + "public_subnets_map": publicSubnetsMap, + "tgw_subnets_map": tgwSubnetsMap, + "subnets_bit_length": subnetsBitLength, + + "availability_zones": availabilityZones, + "number_of_AZs": numberOfAZs, + + "nat_gw_subnet_1_cidr": "10.0.13.0/24", + "nat_gw_subnet_2_cidr": "10.0.23.0/24", + + "gwlbe_subnet_1_cidr": "10.0.14.0/24", + "gwlbe_subnet_2_cidr": "10.0.24.0/24", + + "key_name": keyName, + "enable_volume_encryption": enableVolumeEncryption, + "volume_size": volumeSize, + "enable_instance_connect": enableInstanceConnect, + "disable_instance_termination": disableInstanceTermination, + "allow_upload_download": allowUploadDownload, + "management_server": managementExpectedName, + "configuration_template": configurationTemplate, + "admin_shell": adminShell, + + "gateway_load_balancer_name": gwlbExpectedName, + "target_group_name": targetGroup1Name, + "enable_cross_zone_load_balancing": enableCrossZoneLoadBalancing, + + "gateway_name": gatewayExpectedName, + "gateway_instance_type": gatewayInstanceType, + "minimum_group_size": autoscaleGroupExpectedCapacityMin, + "maximum_group_size": autoscaleGroupExpectedCapacityMax, + "gateway_version": version, + "gateway_password_hash": passwordHash, + "gateway_maintenance_mode_password_hash": passwordHash, + "gateway_SICKey": SICKey, + "gateways_provision_address_type": gatewaysProvisionAddressType, + "allocate_public_IP": allocatePublicIP, + "enable_cloudwatch": enableCloudWatch, + "gateway_bootstrap_script": gatewayBootstrapScript, + + "management_deploy": managementDeploy, + "management_instance_type": managementInstanceType, + "management_version": version, + "management_password_hash": passwordHash, + "management_maintenance_mode_password_hash": passwordHash, + "gateways_policy": gatewaysPolicy, + "gateway_management": gatewayManagement, + "admin_cidr": anywhereAddress, + "gateways_addresses": anywhereAddress, + + "volume_type": volumeType, + }, + + // Set environment variables when running Terraform + EnvVars: envVars, + } + return terraformOptions +} + +func ValidateOutputsTgwGwlbMaster(t *testing.T, terraformOptions *terraform.Options) { + outputDeployment := terraform.Output(t, terraformOptions, "Deployment") + outputManagementPublicIP := terraform.Output(t, terraformOptions, "management_public_ip") + outputGWLBARN := terraform.Output(t, terraformOptions, "gwlb_arn") + outputGWLBServiceName := terraform.Output(t, terraformOptions, "gwlb_service_name") + outputGWLBName := terraform.Output(t, terraformOptions, "gwlb_name") + outputGWLBControllerName := terraform.Output(t, terraformOptions, "controller_name") + outputConfigurationTemplateName := terraform.Output(t, terraformOptions, "template_name") + + assert.Equal(t, outputGWLBName, gwlbExpectedName) + assert.Equal(t, outputGWLBControllerName, gwlbControlllerExpectedName) + assert.Equal(t, outputConfigurationTemplateName, configurationTemplate) + + assert.NotEmpty(t, outputDeployment) + assert.NotEmpty(t, outputManagementPublicIP) + assert.NotEmpty(t, outputGWLBARN) + assert.NotEmpty(t, outputGWLBServiceName) +} diff --git a/deprecated/terraform/aws/R81/tgw-asg-master/README.md b/deprecated/terraform/aws/R81/tgw-asg-master/README.md new file mode 100755 index 00000000..211549c8 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg-master/README.md @@ -0,0 +1,224 @@ +# Check Point CloudGuard Network Transit Gateway Auto Scaling Group Master Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group for Transit Gateway with an optional Management Server in a new VPC. + +These types of Terraform resources are supported: +* [VPC](https://www.terraform.io/docs/providers/aws/r/vpc.html) +* [Subnet](https://www.terraform.io/docs/providers/aws/r/subnet.html) +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [CloudGuard Network for AWS Transit Gateway R80.10 and Higher Deployment Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_AWS_Transit_Gateway/Content/Topics-AWS-TGW-R80-10-AG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/tgw-asg +- /terraform/aws/autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role +- /terraform/aws/modules/vpc + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/tgw-asg-master/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/tgw-asg, /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/tgw-asg, /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/tgw-asg-master/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/tgw-asg-master/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + subnets_bit_length = 8 + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-gateway" + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = true + asn = "6500" + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + management_permissions = "Create with read-write permissions" + management_predefined_role = "" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + gateway_management = "Locally managed" + + // --- Automatic Provisioning with Security Management Server Settings --- + control_gateway_over_public_or_private_address = "private" + management_server = "management-server" + configuration_template = "template-name" + ``` + +- Conditional creation + - To create a Security Management server with IAM Role: + ``` + management_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + ``` + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Gateway | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| asn | The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways | string | n/a | 6500 | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| management_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read-write permissions | no | +| management_predefined_role | ((Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing' | string | n/a | "" | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | Allow gateways only from this network to communicate with the Security Management Server | string | valid CIDR | n/a | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| control_gateway_over_public_or_private_address | Determines if the gateways are provisioned using their private or public address | string | - private
- public | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | management-server | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | TGW-ASG-configuration | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| vpc_id | The id of the deployed vpc | +| public_subnets_ids_list | A list of the public subnets ids | +| management_instance_name | The deployed Security Management AWS instance name | +| management_public_ip | The deployed Security Management Server AWS public ip | +| management_url | URL to the portal of the deployed Security Management Server | +| autoscaling_group_name | The name of the deployed AutoScaling Group | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|-------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | First release of Check Point Transit Gateway Auto Scaling Group Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/tgw-asg-master/locals.tf b/deprecated/terraform/aws/R81/tgw-asg-master/locals.tf new file mode 100755 index 00000000..467c4b4e --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg-master/locals.tf @@ -0,0 +1,66 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.management_permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.management_permissions) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_asn = "^[0-9]+$" + // Will fail if var.asn is invalid + regex_asn = regex(local.regex_valid_asn, var.asn) == var.asn ? 0 : "Variable [asn] must be a valid asn" + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^[0-9a-zA-Z-._]+$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^[0-9a-zA-Z-._]+$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-asg-master/main.tf b/deprecated/terraform/aws/R81/tgw-asg-master/main.tf new file mode 100755 index 00000000..a9fdd06e --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg-master/main.tf @@ -0,0 +1,55 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +// --- VPC --- +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = {} + subnets_bit_length = var.subnets_bit_length +} + +module "launch_tgw_asg_into_vpc" { + source = "../tgw-asg" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + gateways_subnets = module.launch_vpc.public_subnets_ids_list + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + gateways_min_group_size = var.gateways_min_group_size + gateways_max_group_size = var.gateways_max_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + enable_cloudwatch = var.enable_cloudwatch + asn = var.asn + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + management_permissions = var.management_permissions + management_predefined_role = var.management_predefined_role + gateways_blades = var.gateways_blades + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + gateway_management = var.gateway_management + control_gateway_over_public_or_private_address = var.control_gateway_over_public_or_private_address + management_server = var.management_server + configuration_template = var.configuration_template +} diff --git a/deprecated/terraform/aws/R81/tgw-asg-master/output.tf b/deprecated/terraform/aws/R81/tgw-asg-master/output.tf new file mode 100755 index 00000000..ed183c0a --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg-master/output.tf @@ -0,0 +1,24 @@ +output "vpc_id" { + value = module.launch_vpc.vpc_id +} +output "public_subnets_ids_list" { + value = module.launch_vpc.public_subnets_ids_list +} +output "management_instance_name" { + value = module.launch_tgw_asg_into_vpc.management_instance_name +} +output "configuration_template" { + value = module.launch_tgw_asg_into_vpc.configuration_template +} +output "controller_name" { + value = module.launch_tgw_asg_into_vpc.controller_name +} +output "management_public_ip" { + value = module.launch_tgw_asg_into_vpc.management_public_ip +} +output "management_url" { + value = module.launch_tgw_asg_into_vpc.management_url +} +output "autoscaling_group_name" { + value = module.launch_tgw_asg_into_vpc.autoscaling_group_name +} diff --git a/deprecated/terraform/aws/R81/tgw-asg-master/terraform.tfvars b/deprecated/terraform/aws/R81/tgw-asg-master/terraform.tfvars new file mode 100755 index 00000000..7807cc3d --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg-master/terraform.tfvars @@ -0,0 +1,47 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +subnets_bit_length = 8 + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-gateway" +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true +asn = "6500" + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +management_permissions = "Create with read-write permissions" +management_predefined_role = "" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" +gateway_management = "Locally managed" + +// --- Automatic Provisioning with Security Management Server Settings --- +control_gateway_over_public_or_private_address = "private" +management_server = "management-server" +configuration_template = "template-name" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-asg-master/variables.tf b/deprecated/terraform/aws/R81/tgw-asg-master/variables.tf new file mode 100755 index 00000000..a709a74f --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg-master/variables.tf @@ -0,0 +1,217 @@ +// Module: Check Point CloudGuard Network Transit Gateway Auto Scaling Group +// Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server in a new VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" + default = true +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "asn" { + type = string + description = "The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways" + default = "6500" +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "management_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read-write permissions" +} +variable "management_predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'" + default = "" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "management-server" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "TGW-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} diff --git a/deprecated/terraform/aws/R81/tgw-asg-master/versions.tf b/deprecated/terraform/aws/R81/tgw-asg-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/tgw-asg/README.md b/deprecated/terraform/aws/R81/tgw-asg/README.md new file mode 100755 index 00000000..8f09e0cf --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg/README.md @@ -0,0 +1,214 @@ +# Check Point CloudGuard Network Transit Gateway Auto Scaling Group Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Gateway Auto Scaling Group for Transit Gateway with an optional Management Server into an existing VPC. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [CloudWatch Metric Alarm](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/cloudwatch_metric_alarm) +* [EIP](https://www.terraform.io/docs/providers/aws/r/eip.html) +* [Launch template](https://www.terraform.io/docs/providers/aws/r/launch_template.html) +* [Auto Scaling Group](https://www.terraform.io/docs/providers/aws/r/autoscaling_group.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [CloudGuard Network for AWS Transit Gateway R80.10 and Higher Deployment Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_AWS_Transit_Gateway/Content/Topics-AWS-TGW-R80-10-AG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale +- /terraform/aws/management +- /terraform/aws/cme-iam-role + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/tgw-asg/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/tgw-asg/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + +- Variables are configured in /terraform/aws/tgw-asg/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- Network Configuration --- + vpc_id = "vpc-12345678" + gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + + // --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-gateway" + gateway_instance_type = "c5.xlarge" + gateways_min_group_size = 2 + gateways_max_group_size = 8 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + enable_cloudwatch = true + asn = "6500" + + // --- Check Point CloudGuard Network Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + management_permissions = "Create with read-write permissions" + management_predefined_role = "" + gateways_blades = true + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + gateway_management = "Locally managed" + + // --- Automatic Provisioning with Security Management Server Settings --- + control_gateway_over_public_or_private_address = "private" + management_server = "management-server" + configuration_template = "template-name" + ``` + +- Conditional creation + - To create a Security Management server with IAM Role: + ``` + management_permissions = "Create with read permissions" | "Create with read-write permissions" | "Create with assume role permissions (specify an STS role ARN)" + ``` + - To enable cloudwatch for ASG: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------|----------| +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | list(string) | n/a | n/a | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Gateway | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81-BYOL
- R81-PAYG-NGTP
- R81-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.10-BYOL
- R81.10-PAYG-NGTP
- R81.10-PAYG-NGTX
- R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SIC_Key | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| asn | The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways | string | n/a | 6500 | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| management_permissions | IAM role to attach to the instance profile | string | - None (configure later)
- Use existing (specify an existing IAM role name)
- Create with assume role permissions (specify an STS role ARN)
- Create with read permissions
- Create with read-write permissions | Create with read-write permissions | no | +| management_predefined_role | ((Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing' | string | n/a | "" | no | +| gateways_blades | Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later) | bool | true/false | true | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | Allow gateways only from this network to communicate with the Security Management Server | string | valid CIDR | n/a | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address | string | - Locally managed
- Over the internet | Locally managed | no | +| control_gateway_over_public_or_private_address | Determines if the gateways are provisioned using their private or public address | string | - private
- public | private | no | +| management_server | (Optional) The name that represents the Security Management Server in the automatic provisioning configuration | string | n/a | management-server | no | +| configuration_template | (Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration | string | n/a | TGW-ASG-configuration | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| management_instance_name | The deployed Security Management AWS instance name | +| management_public_ip | The deployed Security Management Server AWS public ip | +| management_url | URL to the portal of the deployed Security Management Server | +| autoscaling_group_name | The name of the deployed AutoScaling Group | +| configuration_template | The name that represents the configuration template. Configurations required to automatically provision the Gateways in the Auto Scaling Group, such as what Security Policy to install and which Blades to enable, will be placed under this template name | +| controller_name | The name that represents the controller. Configurations required to connect to your AWS environment, such as credentials and regions, will be placed under this controller name | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230626 | Fixed missing x-chkp-* tags on Auto Scale Group | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20210329 | First release of Check Point Transit Gateway Auto Scaling Group Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/tgw-asg/locals.tf b/deprecated/terraform/aws/R81/tgw-asg/locals.tf new file mode 100755 index 00000000..7ecd5cf4 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg/locals.tf @@ -0,0 +1,64 @@ +locals { + permissions_allowed_values = [ + "None (configure later)", + "Use existing (specify an existing IAM role name)", + "Create with assume role permissions (specify an STS role ARN)", + "Create with read permissions", + "Create with read-write permissions"] + // Will fail if var.management_permissions is invalid + validate_permissions = index(local.permissions_allowed_values, var.management_permissions) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.control_gateway_over_public_or_private_address) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_asn = "^[0-9]+$" + // Will fail if var.asn is invalid + regex_asn = regex(local.regex_valid_asn, var.asn) == var.asn ? 0 : "Variable [asn] must be a valid asn" + + regex_valid_admin_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^[0-9a-zA-Z-._]+$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^[0-9a-zA-Z-._]+$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-asg/main.tf b/deprecated/terraform/aws/R81/tgw-asg/main.tf new file mode 100755 index 00000000..8b7b3cf1 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg/main.tf @@ -0,0 +1,64 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "autoscale" { + source = "../autoscale" + providers = { + aws = aws + } + + vpc_id = var.vpc_id + subnet_ids = var.gateways_subnets + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + enable_instance_connect = var.enable_instance_connect + metadata_imdsv2_required = var.metadata_imdsv2_required + minimum_group_size = var.gateways_min_group_size + maximum_group_size = var.gateways_max_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding tgw identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: autoscale_tgw' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"autoscale_tgw\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo 'Setting ASN to: ${var.asn}'; clish -c 'set as ${var.asn}' -s; echo -e '\nFinished Bootstrap script\n'" + gateways_provision_address_type = var.control_gateway_over_public_or_private_address + management_server = var.management_server + configuration_template = var.configuration_template +} + +data "aws_region" "current"{} + +module "management" { + providers = { + aws = aws + } + count = local.deploy_management_condition ? 1 : 0 + source = "../management" + + vpc_id = var.vpc_id + subnet_id = var.gateways_subnets[0] + management_name = var.management_server + management_instance_type = var.management_instance_type + key_name = var.key_name + allocate_and_associate_eip = true + volume_encryption = var.enable_volume_encryption ? "alias/aws/ebs" : "" + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + iam_permissions = var.management_permissions + predefined_role = var.management_predefined_role + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + allow_upload_download = var.allow_upload_download + admin_cidr = var.admin_cidr + gateway_addresses = var.gateways_addresses + gateway_management = var.gateway_management + management_bootstrap_script = "echo -e '\nStarting Bootstrap script\n'; echo 'Adding tgw identifier to cloud-version'; cv_path='/etc/cloud-version'\n if test -f \"$cv_path\"; then sed -i '/template_name/c\\template_name: management_tgw_asg' /etc/cloud-version; fi; cv_json_path='/etc/cloud-version.json'\n cv_json_path_tmp='/etc/cloud-version-tmp.json'\n if test -f \"$cv_json_path\"; then cat \"$cv_json_path\" | jq '.template_name = \"'\"management_tgw_asg\"'\"' > \"$cv_json_path_tmp\"; mv \"$cv_json_path_tmp\" \"$cv_json_path\"; fi; echo 'Configuring VPN community: tgw-community'; [[ -d /opt/CPcme/menu/additions ]] && /opt/CPcme/menu/additions/config-community.sh \"tgw-community\" || /etc/fw/scripts/autoprovision/config-community.sh \"tgw-community\"; echo 'Setting VPN rules'; mgmt_cli -r true add access-layer name 'Inline'; mgmt_cli -r true add access-rule layer Network position 1 name 'tgw-community VPN Traffic Rule' vpn.directional.1.from 'tgw-community' vpn.directional.1.to 'tgw-community' vpn.directional.2.from 'tgw-community' vpn.directional.2.to External_clear action 'Apply Layer' inline-layer 'Inline'; mgmt_cli -r true add nat-rule package standard position bottom install-on 'Policy Targets' original-source All_Internet translated-source All_Internet method hide; echo 'Creating CME configuration'; autoprov_cfg -f init AWS -mn ${var.management_server} -tn ${var.configuration_template} -cn tgw-controller -po Standard -otp ${var.gateway_SICKey} -r ${data.aws_region.current.name} -ver ${split("-", var.gateway_version)[0]} -iam -dt TGW; autoprov_cfg -f set controller AWS -cn tgw-controller -sv -com tgw-community; autoprov_cfg -f set template -tn ${var.configuration_template} -vpn -vd '''' -con tgw-community; ${var.gateways_blades} && autoprov_cfg -f set template -tn ${var.configuration_template} -ia -ips -appi -av -ab; echo -e '\nFinished Bootstrap script\n'" +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-asg/output.tf b/deprecated/terraform/aws/R81/tgw-asg/output.tf new file mode 100755 index 00000000..8a282a53 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg/output.tf @@ -0,0 +1,18 @@ +output "management_instance_name" { + value = module.management[0].management_instance_name +} +output "configuration_template" { + value = var.configuration_template +} +output "controller_name" { + value = "tgw-controller" +} +output "management_public_ip" { + value = module.management[0].management_public_ip +} +output "management_url" { + value = module.management[0].management_url +} +output "autoscaling_group_name" { + value = module.autoscale.autoscale_autoscaling_group_name +} diff --git a/deprecated/terraform/aws/R81/tgw-asg/terraform.tfvars b/deprecated/terraform/aws/R81/tgw-asg/terraform.tfvars new file mode 100755 index 00000000..943f16b4 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- Network Configuration --- +vpc_id = "vpc-12345678" +gateways_subnets = ["subnet-123b5678", "subnet-123a4567"] + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-gateway" +gateway_instance_type = "c5.xlarge" +gateways_min_group_size = 2 +gateways_max_group_size = 8 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +enable_cloudwatch = true +asn = "65000" + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +management_permissions = "Create with read-write permissions" +management_predefined_role = "" +gateways_blades = true +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" +gateway_management = "Locally managed" + +// --- Automatic Provisioning with Security Management Server Settings --- +control_gateway_over_public_or_private_address = "private" +management_server = "management-server" +configuration_template = "template-name" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-asg/variables.tf b/deprecated/terraform/aws/R81/tgw-asg/variables.tf new file mode 100755 index 00000000..9a9a47e1 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg/variables.tf @@ -0,0 +1,211 @@ +// Module: Check Point CloudGuard Network Transit Gateway Auto Scaling Group +// Deploy an Auto Scaling Group of CloudGuard Security Gateways for Transit Gateway with an optional Management Server into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- Network Configuration --- +variable "vpc_id" { + type = string +} +variable "gateways_subnets" { + type = list(string) + description = "Select at least 2 external subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} + +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" + default = true +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} + +// --- Check Point CloudGuard Network Security Gateways Auto Scaling Group Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Gateway" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_gateway_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "gateways_min_group_size" { + type = number + description = "The minimal number of Security Gateways" + default = 2 +} +variable "gateways_max_group_size" { + type = number + description = "The maximal number of Security Gateways" + default = 10 +} +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "asn" { + type = string + description = "The organization Autonomous System Number (ASN) that identifies the routing domain for the Security Gateways" + default = "6500" +} + +// --- Check Point CloudGuard Network Security Management Server Configuration --- +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "(optional) Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command 'grub2-mkpasswd-pbkdf2' on Linux and paste it here)." + type = string + default = "" +} +variable "management_permissions" { + type = string + description = "IAM role to attach to the instance profile" + default = "Create with read-write permissions" +} +variable "management_predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the instance profile. Ignored if IAM role is not set to 'Use existing'" + default = "" +} +variable "gateways_blades" { + type = bool + description = "Turn on the Intrusion Prevention System, Application Control, Anti-Virus and Anti-Bot Blades (additional Blades can be manually turned on later)" + default = true +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address" + default = "Locally managed" +} + +// --- Automatic Provisioning with Security Management Server Settings --- +variable "control_gateway_over_public_or_private_address" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} +variable "management_server" { + type = string + description = "(Optional) The name that represents the Security Management Server in the automatic provisioning configuration" + default = "management-server" +} +variable "configuration_template" { + type = string + description = "(Optional) A name of a Security Gateway configuration template in the automatic provisioning configuration" + default = "TGW-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} diff --git a/deprecated/terraform/aws/R81/tgw-asg/versions.tf b/deprecated/terraform/aws/R81/tgw-asg/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-asg/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/README.md b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/README.md new file mode 100755 index 00000000..db75e948 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/README.md @@ -0,0 +1,208 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster for Transit Gateway Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster with a new VPC on AWS for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply -target=aws_route_table.private_subnet_rtb -auto-approve && terraform apply + ``` + + - Variables are configured in /terraform/aws/cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + } + private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 + } + tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 + } + subnets_bit_length = 8 + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1 \"us-east-1b\" = 2} ) | map | n/a | n/a | yes | +| private_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3 \"us-east-1b\" = 4} ) | map | n/a | n/a | yes | +| tgw_subnets_map | A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------|-----------------------------------| +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221123 | R81.20 version support | +| 20221229 | Removed unsupported versions | +| 20221123 | First release of Check Point Security Cluster Terraform module for AWS | + + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/locals.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/locals.tf new file mode 100755 index 00000000..387fb7c1 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/locals.tf @@ -0,0 +1,61 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/main.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/main.tf new file mode 100755 index 00000000..d04b9548 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/main.tf @@ -0,0 +1,73 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = var.private_subnets_map + tgw_subnets_map = var.tgw_subnets_map + subnets_bit_length = var.subnets_bit_length +} +resource "aws_route_table" "private_subnet_rtb" { + depends_on = [module.launch_vpc] + vpc_id = module.launch_vpc.vpc_id + tags = { + Name = "Private Subnets Route Table" + } +} +resource "aws_route_table_association" "private_rtb_to_private_subnet1" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[0] +} +resource "aws_route_table_association" "private_rtb_to_private_subnet2" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + route_table_id = aws_route_table.private_subnet_rtb.id + subnet_id = module.launch_vpc.private_subnets_ids_list[1] +} +module "tgw_cluster_into_vpc" { + depends_on = [module.launch_vpc, aws_route_table.private_subnet_rtb] + source = "../tgw-cross-az-cluster" + providers = { + aws = aws + } + + vpc_id = module.launch_vpc.vpc_id + public_subnet_1 = module.launch_vpc.public_subnets_ids_list[0] + public_subnet_2 = module.launch_vpc.public_subnets_ids_list[1] + private_subnet_1 = module.launch_vpc.private_subnets_ids_list[0] + private_subnet_2 = module.launch_vpc.private_subnets_ids_list[1] + tgw_subnet_1_id = module.launch_vpc.tgw_subnets_ids_list[0] + tgw_subnet_2_id =module.launch_vpc.tgw_subnets_ids_list[1] + private_route_table = aws_route_table.private_subnet_rtb.id + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + memberAToken = var.memberAToken + memberBToken = var.memberBToken + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + volume_type = var.volume_type +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/output.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/output.tf new file mode 100755 index 00000000..fd143a67 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/output.tf @@ -0,0 +1,30 @@ +output "cluster_public_ip" { + value = module.tgw_cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.tgw_cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.tgw_cluster_into_vpc.member_b_public_ip +} +output "member_a_ssh" { + value = module.tgw_cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.tgw_cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.tgw_cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.tgw_cluster_into_vpc.member_b_url +} +output "member_a_eni" { + value = module.tgw_cluster_into_vpc.member_a_eni +} +output "member_b_eni" { + value = module.tgw_cluster_into_vpc.member_b_eni +} +output "vpc_id" { + value = module.launch_vpc.vpc_id +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/terraform.tfvars b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/terraform.tfvars new file mode 100755 index 00000000..2a1fee10 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/terraform.tfvars @@ -0,0 +1,48 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.29.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 +} +private_subnets_map = { + "us-east-1a" = 3 + "us-east-1b" = 4 +} +tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 +} +subnets_bit_length = 8 + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true + +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/variables.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/variables.tf new file mode 100755 index 00000000..1485389b --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/variables.tf @@ -0,0 +1,200 @@ +// Module: Check Point CloudGuard Network Security Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// ---VPC Network Configuration --- +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +resource "null_resource" "tgw_availability_zones_validation1" { + count = length(var.public_subnets_map) == 2 ? 0 : "variable public_subnets_map size must be equal to variable 2" +} +variable "private_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 2} ) " +} +resource "null_resource" "tgw_availability_zones_validation2" { + count = length(var.private_subnets_map) == 2 ? 0 : "variable private_subnets_map size must be equal to variable 2" +} +variable "tgw_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 3} ) " +} +resource "null_resource" "tgw_availability_zones_validation3" { + count = length(var.tgw_subnets_map) == 2 ? 0 : "variable tgw_subnets_map size must be equal to variable 2" +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} + + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/versions.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster/README.md b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/README.md new file mode 100755 index 00000000..fb62e2fe --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/README.md @@ -0,0 +1,204 @@ +# Check Point CloudGuard Network Security Cross AZ Cluster for Transit Gateway Terraform module for AWS + +Terraform module which deploys a Check Point CloudGuard Network Security Cross AZ Cluster into an existing VPC on AWS for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://www.terraform.io/docs/providers/aws/r/instance.html) +* [Security Group](https://www.terraform.io/docs/providers/aws/r/security_group.html) +* [Network interface](https://www.terraform.io/docs/providers/aws/r/network_interface.html) +* [IAM Role](https://www.terraform.io/docs/providers/aws/r/iam_role.html) - conditional creation + +See the [Deploying a Check Point Cluster in AWS (Amazon Web Services)](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Default.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/modules/amis +- /terraform/aws/modules/cluster-iam-role + + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/cluster/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/cluster/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` +- Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/cluster/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-1234" + public_subnet_1 = "subnet-1234" + public_subnet_2 = "subnet-2345" + private_subnet_1 = "subnet-3456" + private_subnet_2 = "subnet-4567" + tgw_subnet_1_id = "subnet-5678" + tgw_subnet_2_id = "subnet-6789" + private_route_table = "" + + // --- EC2 Instance Configuration --- + gateway_name = "Check-Point-Cluster-tf" + gateway_instance_type = "c5.xlarge" + key_name = "publickey" + allocate_and_associate_eip = true + volume_size = 100 + volume_encryption = "alias/aws/ebs" + enable_instance_connect = false + disable_instance_termination = false + instance_tags = { + key1 = "value1" + key2 = "value2" + } + predefined_role = "" + + // --- Check Point Settings --- + gateway_version = "R81.20-BYOL" + admin_shell = "/etc/cli.sh" + gateway_SICKey = "12345678" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + + // --- Quick connect to Smart-1 Cloud (Recommended) --- + memberAToken = "" + memberBToken = "" + + // --- Advanced Settings --- + resources_tag_name = "tag-name" + gateway_hostname = "gw-hostname" + allow_upload_download = true + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + primary_ntp = "" + secondary_ntp = "" + ``` + +- Conditional creation + - To create an Elastic IP and associate it to each cluster member instance: + ``` + allocate_and_associate_eip = "true" + ``` + - To create IAM Role: + ``` + predefined_role = "" + ``` + - To create route from '0.0.0.0/0' to the Active Cluster member instance, please provide route table: + ``` + private_route_table = "rtb-12345678" + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + ### Optional re-deploy of cluster member: + In case of re-deploying one cluster member, make sure that it's in STANDBY state, and the second member is the ACTIVE one. + Follow the commands below in order to re-deploy (replace MEMBER with a or b): + - terraform taint aws_instance.member-MEMBER-instance + - terraform plan (review the changes) + - terraform apply + - In Smart Console: reset SIC with the re-deployed member and install policy + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|----------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------|----------| +| vpc_id | The VPC id in which to deploy | string | n/a | n/a | yes | +| public_subnet_id | The public subnet of the cluster. The cluster's public IPs will be generated from this subnet | string | n/a | n/a | yes | +| private_subnet_id | The private subnet of the cluster. The cluster's private IPs will be generated from this subnet | string | n/a | n/a | yes | +| tgw_subnet_1_id | The TGW attachment subnet ID located in the 1st Availability Zone | string | n/a | n/a | yes | +| tgw_subnet_2_id | The TGW attachment subnet ID located in the 2st Availability Zone | string | n/a | n/a | yes | +| private_route_table | (Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route | string | n/a | "" | no | +| gateway_name | (Optional) The name tag of the Security Gateway instances | string | n/a | Check-Point-Cluster-tf | no | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| key_name | The EC2 Key Pair name to allow SSH access to the instance | string | n/a | n/a | yes | +| allocate_and_associate_eip | If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP | bool | true/false | true | no | +| volume_size | Root volume size (GB) - minimum 100 | number | n/a | 100 | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| volume_encryption | KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs') | string | n/a | alias/aws/ebs | no | +| enable_instance_connect | Enable AWS Instance Connect. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| instance_tags | (Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances | map(string) | n/a | {} | no | +| predefined_role | (Optional) A predefined IAM role to attach to the cluster profile | string | n/a | "" | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| memberAToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| memberBToken | (Recommended) Quick connect to Smart-1 Cloud. Paste here the token copied from the Connect Gateway screen in Smart-1 Cloud portal. Follow the instructions in SK180501 to quickly connect this Gateway to Smart-1 Cloud. | string | n/a | "" | no | +| resources_tag_name | (Optional) Name tag prefix of the resources | string | n/a | "" | no | +| gateway_hostname | (Optional) The host name will be appended with member-a/b accordingly. The name must not contain reserved words. For details, refer to sk40179. | string | n/a | "" | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) Semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| primary_ntp | (Optional) The IPv4 addresses of Network Time Protocol primary server | string | n/a | 169.254.169.123 | no | +| secondary_ntp | (Optional) The IPv4 addresses of Network Time Protocol secondary server | string | n/a | 0.pool.ntp.org | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|--------------------|-----------------------------------| +| cluster_public_ip | The public address of the cluster | +| member_a_public_ip | The public address of member A | +| member_b_public_ip | The public address of member B | +| member_a_ssh | SSH command to member A | +| member_b_ssh | SSH command to member B | +| member_a_url | URL to the member A portal | +| member_b_url | URL to the member B portal | + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20230521 | - Change default shell for the admin user to /etc/cli.sh
- Add description for reserved words in hostname | +| 20230503 | Smart-1 Cloud token validation | +| 20230411 | - Improved deployment experience for gateways and clusters managed by Smart-1 Cloud
- Multiple VIPs support for Cross Availability Zone Cluster. For more details refer to the [Cross Availability Zone Cluster for AWS R81.20 Administration Guide](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_for_AWS_Cross_AZ_Cluster/Content/Topics-AWS-CrossAZ-Cluster-AG/Check-Point-CloudGuard-for-AWS.htm) -> "Deploying Cross AZ Cluster with multiple VIPs" section. | +| 20221229 | Removed unsupported versions | +| 20221123 | R81.20 version support | +| 20221123 | First release of Check Point Security Cluster Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster/locals.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/locals.tf new file mode 100755 index 00000000..9a9929b7 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/locals.tf @@ -0,0 +1,60 @@ +locals { + admin_shell_allowed_values = [ + "/etc/cli.sh", + "/bin/bash", + "/bin/csh", + "/bin/tcsh"] + // Will fail if var.admin_shell is invalid + validate_admin_shell = index(local.admin_shell_allowed_values, var.admin_shell) + + create_iam_role = var.predefined_role == "" ? 1 : 0 + provided_roue_table = var.private_route_table == "" ? 0 : 1 + internal_route_table_condition = var.private_route_table != "" ? 1 : 0 + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + is_both_tokens_used = length(var.memberAToken) > 0 == length(var.memberBToken) > 0 + validation_message_both = "Smart-1 Cloud Tokens for member A and member B can not be empty." + //Will fail if var.memberAToken is empty and var.memberBToken isn't and vice versa + regex_s1c_validate = regex("^$", (local.is_both_tokens_used ? "" : local.validation_message_both)) + + is_tokens_used = length(var.memberAToken) > 0 + is_both_tokens_the_same = var.memberAToken == var.memberBToken + validation_message_unique = "The same Smart-1 Cloud token is used for the two Cluster members. Each Cluster member must have a unique token" + //Will fail if both s1c tokens are the same + regex_s1c_unique = local.is_tokens_used ? regex("^$", (local.is_both_tokens_the_same ? local.validation_message_unique : "")) : "" + + regex_valid_gateway_hostname = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.gateway_hostname is invalid + regex_gateway_hostname = regex(local.regex_valid_gateway_hostname, var.gateway_hostname) == var.gateway_hostname ? 0 : "Variable [gateway_hostname] must be a valid hostname label or an empty string" + volume_encryption_condition = var.volume_encryption != "" ? true : false + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_primary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.primary_ntp is invalid + regex_primary_ntp = regex(local.regex_valid_primary_ntp, var.primary_ntp) == var.primary_ntp ? 0 : "Variable [primary_ntp] must be a valid ntp" + + regex_valid_secondary_ntp = "^[\\.a-zA-Z0-9\\-]*$" + // Will fail if var.secondary_ntp is invalid + regex_secondary_ntp = regex(local.regex_valid_secondary_ntp, var.secondary_ntp) == var.secondary_ntp ? 0 : "Variable [secondary_ntp] must be a valid ntp" + + gateway_bootstrap_script64 = base64encode(var.gateway_bootstrap_script) + //Splits the version and licence and returns the os version + version_split = element(split("-", var.gateway_version), 0) + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster/main.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/main.tf new file mode 100755 index 00000000..4ae319ab --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/main.tf @@ -0,0 +1,62 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + + +module "cluster_into_vpc" { + source = "../cross-az-cluster" + providers = { + aws = aws + } + + vpc_id = var.vpc_id + public_subnet_ids = tolist([var.public_subnet_1, var.public_subnet_2]) + private_subnet_ids = tolist([var.private_subnet_1, var.private_subnet_2]) + private_route_table = var.private_route_table + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + key_name = var.key_name + volume_size = var.volume_size + volume_encryption = var.volume_encryption + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + instance_tags = var.instance_tags + predefined_role = var.predefined_role + gateway_version = var.gateway_version + admin_shell = var.admin_shell + gateway_SICKey = var.gateway_SICKey + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + memberAToken = var.memberAToken + memberBToken = var.memberBToken + resources_tag_name = var.resources_tag_name + gateway_hostname = var.gateway_hostname + allow_upload_download = var.allow_upload_download + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + primary_ntp = var.primary_ntp + secondary_ntp = var.secondary_ntp + volume_type = var.volume_type +} +resource "aws_route_table" "tgw_route_table" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + network_interface_id = module.cluster_into_vpc.member_a_eni + } + tags = { + Name = "TGW Attachment Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment1_rtb_assoc" { + subnet_id = var.tgw_subnet_1_id + route_table_id = aws_route_table.tgw_route_table.id +} +resource "aws_route_table_association" "tgw_attachment2_rtb_assoc" { + subnet_id = var.tgw_subnet_2_id + route_table_id = aws_route_table.tgw_route_table.id +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster/output.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/output.tf new file mode 100755 index 00000000..2aa6d333 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/output.tf @@ -0,0 +1,27 @@ +output "cluster_public_ip" { + value = module.cluster_into_vpc.cluster_public_ip +} +output "member_a_public_ip" { + value = module.cluster_into_vpc.member_a_public_ip +} +output "member_b_public_ip" { + value = module.cluster_into_vpc.member_b_public_ip +} +output "member_a_eni" { + value = module.cluster_into_vpc.member_a_eni +} +output "member_a_ssh" { + value = module.cluster_into_vpc.member_a_ssh +} +output "member_b_ssh" { + value = module.cluster_into_vpc.member_b_ssh +} +output "member_a_url" { + value = module.cluster_into_vpc.member_a_url +} +output "member_b_url" { + value = module.cluster_into_vpc.member_b_url +} +output "member_b_eni" { + value = module.cluster_into_vpc.member_b_eni +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster/terraform.tfvars b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/terraform.tfvars new file mode 100755 index 00000000..c1008d0d --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/terraform.tfvars @@ -0,0 +1,43 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-1234" +public_subnet_1 = "subnet-1234" +public_subnet_2 = "subnet-2345" +private_subnet_1 = "subnet-3456" +private_subnet_2 = "subnet-4567" +tgw_subnet_1_id = "subnet-5678" +tgw_subnet_2_id = "subnet-6789" +private_route_table = "" + +// --- EC2 Instance Configuration --- +gateway_name = "Check-Point-Cluster-tf" +gateway_instance_type = "c5.xlarge" +key_name = "publickey" +volume_size = 100 +volume_encryption = "alias/aws/ebs" +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true + +predefined_role = "" + +// --- Check Point Settings --- +gateway_version = "R81.20-BYOL" +admin_shell = "/etc/cli.sh" +gateway_SICKey = "12345678" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + +// --- Quick connect to Smart-1 Cloud (Recommended) --- +memberAToken = "" +memberBToken = "" + +// --- Advanced Settings --- +resources_tag_name = "tag-name" +gateway_hostname = "gw-hostname" +allow_upload_download = true +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" +primary_ntp = "" +secondary_ntp = "" \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster/variables.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/variables.tf new file mode 100755 index 00000000..eb330795 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/variables.tf @@ -0,0 +1,201 @@ +// Module: Check Point CloudGuard Network Security Cluster into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// --- VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "public_subnet_1" { + type = string + description = "The public subnet ID of the cluster that located in the 1st Availability Zone" +} +variable "public_subnet_2" { + type = string + description = "The public subnet of the cluster that located in the 2st Availability Zone" +} +variable "private_subnet_1" { + type = string + description = "The private subnet of the cluster that located in the 1st Availability Zone" +} +variable "private_subnet_2" { + type = string + description = "The private subnet of the cluster that located in the 2st Availability Zone" +} +variable "tgw_subnet_1_id" { + type = string + description = "The TGW attachment subnet ID located in the 1st Availability Zone" +} +variable "tgw_subnet_2_id" { + type = string + description = "The TGW attachment subnet ID located in the 2st Availability Zone" +} +variable "private_route_table" { + type = string + description = "(Optional) Set 0.0.0.0/0 route to the Active Cluster member instance in this route table (e.g. rtb-12a34567). Route table cannot have an existing 0.0.0.0/0 route" + default= "" +} + +// --- EC2 Instance Configuration --- +variable "gateway_name" { + type = string + description = "(Optional) The name tag of the Security Gateway instances" + default = "Check-Point-Cluster-tf" +} +variable "gateway_instance_type" { + type = string + description = "The instance type of the Security Gateways" + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instance" +} +variable "allocate_and_associate_eip" { + type = bool + description = "If set to true, an elastic IP will be allocated and associated with each cluster member, in addition to the shared cluster Elastic IP" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Volume Size validation - resource will not be created if the volume size is smaller than 100 + count = var.volume_size >= 100 ? 0 : "volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "volume_encryption" { + type = string + description = "KMS or CMK key Identifier: Use key ID, alias or ARN. Key alias should be prefixed with 'alias/' (e.g. for KMS default alias 'aws/ebs' - insert 'alias/aws/ebs')" + default = "alias/aws/ebs" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "instance_tags" { + type = map(string) + description = "(Optional) A map of tags as key=value pairs. All tags will be added to the Gateway EC2 Instances" + default = {} +} +variable "predefined_role" { + type = string + description = "(Optional) A predefined IAM role to attach to the cluster profile" + default = "" +} + +// --- Check Point Settings --- +variable "gateway_version" { + type = string + description = "Gateway version and license" + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gateway" + version_license = var.gateway_version +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters" +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +// --- Quick connect to Smart-1 Cloud (Recommended) --- +variable "memberAToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} +variable "memberBToken" { + type = string + description = "Follow the instructions in sk180501 to quickly connect this Cross AZ Cluster to Smart-1 Cloud." +} + +// --- Advanced Settings --- +variable "resources_tag_name" { + type = string + description = "(Optional) Name tag prefix of the resources" + default = "" +} +variable "gateway_hostname" { + type = string + description = "(Optional) The host name will be appended with member-a/b accordingly" + default = "" +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics" + default = false +} +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} +variable "primary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol primary server" + default = "169.254.169.123" +} +variable "secondary_ntp" { + type = string + description = "(Optional) The IPv4 addresses of Network Time Protocol secondary server" + default = "0.pool.ntp.org" +} diff --git a/deprecated/terraform/aws/R81/tgw-cross-az-cluster/versions.tf b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-cross-az-cluster/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/tgw-gwlb-master/README.md b/deprecated/terraform/aws/R81/tgw-gwlb-master/README.md new file mode 100755 index 00000000..edcd4f34 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb-master/README.md @@ -0,0 +1,265 @@ +# Check Point CloudGuard Network Gateway Load Balancer for Transit Gateway Terraform Master module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into new Centralized Security VPC for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/modules/vpc +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +- /terraform/aws/gwlb + +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` + - Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_cidr = "10.0.0.0/16" + public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + "us-east-1c" = 3 + "us-east-1d" = 4 + } + tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 + "us-east-1c" = 7 + "us-east-1d" = 8 + } + subnets_bit_length = 8 + + availability_zones = ["us-east-1a", "us-east-1b", "us-east-1c", "us-east-1d"] + number_of_AZs = 4 + + nat_gw_subnet_1_cidr ="10.0.13.0/24" + nat_gw_subnet_2_cidr = "10.0.23.0/24" + nat_gw_subnet_3_cidr = "10.0.33.0/24" + nat_gw_subnet_4_cidr = "10.0.43.0/24" + + gwlbe_subnet_1_cidr = "10.0.14.0/24" + gwlbe_subnet_2_cidr = "10.0.24.0/24" + gwlbe_subnet_3_cidr = "10.0.34.0/24" + gwlbe_subnet_4_cidr = "10.0.44.0/24" + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb" + target_group_name = "tg1" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "0.0.0.0/0" + gateways_addresses = "0.0.0.0/0" + + // --- Other parameters --- + volume_type = "gp3" + ``` + +- Conditional creation + - To enable cloudwatch for tgw-gwlb-master: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_cidr | The CIDR block of the VPC | string | n/a | n/a | yes | +| subnets_bit_length | Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20 | number | n/a | n/a | yes | +| public_subnets_map | A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 1 pair. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| availability_zones | The Availability Zones (AZs) to use for the subnets in the VPC. | string | n/a | n/a | yes | +| Number_of_AZs | Number of Availability Zones to use in the VPC. | number | n/a | 2 | yes | +| tgw_subnets_map | A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) | map | n/a | n/a | yes | +| nat_gw_subnet_1_cidr | CIDR block for NAT subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.13.0/24 | yes | +| nat_gw_subnet_2_cidr | CIDR block for NAT subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.23.0/24 | yes | +| nat_gw_subnet_3_cidr | CIDR block for NAT subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.33.0/24 | yes | +| nat_gw_subnet_4_cidr | CIDR block for NAT subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.43.0/24 | yes | +| gwlbe_subnet_1_cidr | CIDR block for GWLBe subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.14.0/24 | yes | +| gwlbe_subnet_2_cidr | CIDR block for GWLBe subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.24.0/24 | yes | +| gwlbe_subnet_3_cidr | CIDR block for GWLBe subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.34.0/24 | yes | +| gwlbe_subnet_4_cidr | CIDR block for GWLBe subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.44.0/24 | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-ter | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb-terraform | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1-terraform | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | gwlb-terraform | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|----------------------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point CloudGuar d Network Gateway Load Balancer for Transit Gateway Master Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/tgw-gwlb-master/locals.tf b/deprecated/terraform/aws/R81/tgw-gwlb-master/locals.tf new file mode 100755 index 00000000..d75eeaa5 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb-master/locals.tf @@ -0,0 +1,62 @@ +locals { + regex_valid_vpc_cidr = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/(1[6-9]|2[0-8]))$" + // Will fail if var.vpc_cidr is invalid + regex_vpc_cidr = regex(local.regex_valid_vpc_cidr, var.vpc_cidr) == var.vpc_cidr ? 0 : "Variable [vpc_cidr] must be a valid vpc cidr" + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.volume_type] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) + + + #note: we need to add validiation for every subnet in masters solution +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-gwlb-master/main.tf b/deprecated/terraform/aws/R81/tgw-gwlb-master/main.tf new file mode 100755 index 00000000..3b616ebc --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb-master/main.tf @@ -0,0 +1,85 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + +module "launch_vpc" { + source = "../modules/vpc" + + vpc_cidr = var.vpc_cidr + public_subnets_map = var.public_subnets_map + private_subnets_map = {} + tgw_subnets_map = var.tgw_subnets_map + subnets_bit_length = var.subnets_bit_length +} +module "tgw-gwlb"{ + source = "../tgw-gwlb" + providers = { + aws = aws + } + vpc_id = module.launch_vpc.vpc_id + gateways_subnets = module.launch_vpc.public_subnets_ids_list + number_of_AZs = var.number_of_AZs + availability_zones = var.availability_zones + internet_gateway_id = module.launch_vpc.aws_igw + + transit_gateway_attachment_subnet_1_id = element(module.launch_vpc.tgw_subnets_ids_list, 0) + transit_gateway_attachment_subnet_2_id = element(module.launch_vpc.tgw_subnets_ids_list, 1) + transit_gateway_attachment_subnet_3_id = var.number_of_AZs >= 3 ? element(module.launch_vpc.tgw_subnets_ids_list, 2) : "" + transit_gateway_attachment_subnet_4_id = var.number_of_AZs >= 4 ? element(module.launch_vpc.tgw_subnets_ids_list, 3) : "" + + nat_gw_subnet_1_cidr = var.nat_gw_subnet_1_cidr + nat_gw_subnet_2_cidr = var.nat_gw_subnet_2_cidr + nat_gw_subnet_3_cidr = var.nat_gw_subnet_3_cidr + nat_gw_subnet_4_cidr = var.nat_gw_subnet_4_cidr + + gwlbe_subnet_1_cidr = var.gwlbe_subnet_1_cidr + gwlbe_subnet_2_cidr = var.gwlbe_subnet_2_cidr + gwlbe_subnet_3_cidr = var.gwlbe_subnet_3_cidr + gwlbe_subnet_4_cidr = var.gwlbe_subnet_4_cidr + + // --- General Settings --- + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + volume_size = var.volume_size + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + management_server = var.management_server + configuration_template = var.configuration_template + admin_shell = var.admin_shell + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = var.gateway_load_balancer_name + target_group_name = var.target_group_name + enable_cross_zone_load_balancing = var.enable_cross_zone_load_balancing + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateway_management = var.gateway_management + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + + volume_type = var.volume_type +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-gwlb-master/output.tf b/deprecated/terraform/aws/R81/tgw-gwlb-master/output.tf new file mode 100755 index 00000000..67085776 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb-master/output.tf @@ -0,0 +1,24 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "management_public_ip" { + depends_on = [module.tgw-gwlb] + value = module.tgw-gwlb[*].management_public_ip +} +output "gwlb_arn" { + depends_on = [module.tgw-gwlb] + value = module.tgw-gwlb[*].gwlb_arn +} +output "gwlb_service_name" { + depends_on = [module.tgw-gwlb] + value = module.tgw-gwlb[*].gwlb_service_name +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-gwlb-master/terraform.tfvars b/deprecated/terraform/aws/R81/tgw-gwlb-master/terraform.tfvars new file mode 100755 index 00000000..bdb7a361 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb-master/terraform.tfvars @@ -0,0 +1,76 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_cidr = "10.0.0.0/16" +public_subnets_map = { + "us-east-1a" = 1 + "us-east-1b" = 2 + "us-east-1c" = 3 + "us-east-1d" = 4 +} +tgw_subnets_map = { + "us-east-1a" = 5 + "us-east-1b" = 6 + "us-east-1c" = 7 + "us-east-1d" = 8 +} +subnets_bit_length = 8 + +availability_zones = ["us-east-1a", "us-east-1b", "us-east-1c", "us-east-1d"] +number_of_AZs = 4 + +nat_gw_subnet_1_cidr = "10.0.13.0/24" +nat_gw_subnet_2_cidr = "10.0.23.0/24" +nat_gw_subnet_3_cidr = "10.0.33.0/24" +nat_gw_subnet_4_cidr = "10.0.43.0/24" + +gwlbe_subnet_1_cidr = "10.0.14.0/24" +gwlbe_subnet_2_cidr = "10.0.24.0/24" +gwlbe_subnet_3_cidr = "10.0.34.0/24" +gwlbe_subnet_4_cidr = "10.0.44.0/24" + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R81/tgw-gwlb-master/variables.tf b/deprecated/terraform/aws/R81/tgw-gwlb-master/variables.tf new file mode 100755 index 00000000..af425811 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb-master/variables.tf @@ -0,0 +1,326 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// ---VPC Network Configuration --- +variable "number_of_AZs" { + type = number + description = "Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter" + default = 2 +} +variable "availability_zones"{ + type = list(string) + description = "The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved)" +} +resource "null_resource" "tgw_availability_zones_validation1" { + count = var.number_of_AZs == length(var.availability_zones) ? 0 : "variable availability_zones list size must be equal to variable num_of_AZs" +} +variable "vpc_cidr" { + type = string + description = "The CIDR block of the VPC" + default = "10.0.0.0/16" +} +variable "public_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number}. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +resource "null_resource" "tgw_availability_zones_validation2" { + count = var.number_of_AZs == length(var.public_subnets_map) ? 0 : "variable public_subnets_map size must be equal to variable num_of_AZs" +} +variable "subnets_bit_length" { + type = number + description = "Number of additional bits with which to extend the vpc cidr. For example, if given a vpc_cidr ending in /16 and a subnets_bit_length value of 4, the resulting subnet address will have length /20" +} +variable "tgw_subnets_map" { + type = map(string) + description = "A map of pairs {availability-zone = subnet-suffix-number} for the tgw subnets. Each entry creates a subnet. Minimum 2 pairs. (e.g. {\"us-east-1a\" = 1} ) " +} +resource "null_resource" "tgw_availability_zones_validation3" { + count = var.number_of_AZs == length(var.tgw_subnets_map) ? 0 : "variable tgw_subnets_map size must be equal to variable num_of_AZs" +} +variable "nat_gw_subnet_1_cidr" { + type = string + description = "CIDR block for NAT subnet 1 located in the 1st Availability Zone" + default = "10.0.13.0/24" +} +variable "nat_gw_subnet_2_cidr" { + type = string + description = "CIDR block for NAT subnet 2 located in the 2st Availability Zone" + default = "10.0.23.0/24" +} +variable "nat_gw_subnet_3_cidr" { + type = string + description = "CIDR block for NAT subnet 3 located in the 3st Availability Zone" + default = "10.0.33.0/24" +} +variable "nat_gw_subnet_4_cidr" { + type = string + description = "CIDR block for NAT subnet 4 located in the 4st Availability Zone" + default = "10.0.43.0/24" +} +variable "gwlbe_subnet_1_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 1 located in the 1st Availability Zone" + default = "10.0.14.0/24" +} +variable "gwlbe_subnet_2_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 2 located in the 2st Availability Zone" + default = "10.0.24.0/24" +} +variable "gwlbe_subnet_3_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 3 located in the 3st Availability Zone" + default = "10.0.34.0/24" +} +variable "gwlbe_subnet_4_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 4 located in the 4st Availability Zone" + default = "10.0.44.0/24" +} +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." + default = "gwlb-management-server" +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + default = "gwlb-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + diff --git a/deprecated/terraform/aws/R81/tgw-gwlb-master/versions.tf b/deprecated/terraform/aws/R81/tgw-gwlb-master/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb-master/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +} diff --git a/deprecated/terraform/aws/R81/tgw-gwlb/README.md b/deprecated/terraform/aws/R81/tgw-gwlb/README.md new file mode 100755 index 00000000..e5c3a379 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb/README.md @@ -0,0 +1,264 @@ +# Check Point CloudGuard Network Gateway Load Balancer for Transit Gateway Terraform module for AWS + +Terraform module which deploys an AWS Auto Scaling group configured for Gateway Load Balancer into existing Centralized Security VPC for Transit Gateway. + +These types of Terraform resources are supported: +* [AWS Instance](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/instance) +* [VPC](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/vpc) +* [Security Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/security_group) +* [Load Balancer](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb) +* [Load Balancer Target Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_target_group) +* [Launch template](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/launch_template) +* [Auto Scaling Group](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/autoscaling_group) +* [IAM Role](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/iam_role) - conditional creation + +See the [Check Point CloudGuard Gateway Load Balancer on AWS](https://sc1.checkpoint.com/documents/IaaS/WebAdminGuides/EN/CP_CloudGuard_Network_for_AWS_Centralized_Gateway_Load_Balancer/Content/Topics-AWS-GWLB-VPC-DG/Introduction.htm) for additional information + +This solution uses the following modules: +- /terraform/aws/autoscale-gwlb +- /terraform/aws/management +- /terraform/aws/cme-iam-role-gwlb +- /terraform/aws/modules/amis +- /terraform/aws/gwlb +## Configurations + +The **main.tf** file includes the following provider configuration block used to configure the credentials for the authentication with AWS, as well as a default region for your resources: +``` +provider "aws" { + region = var.region + access_key = var.aws_access_key_ID + secret_key = var.aws_secret_access_key +} +``` +The provider credentials can be provided either as static credentials or as [Environment Variables](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#environment-variables). +- Static credentials can be provided by adding an access_key and secret_key in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: +``` +region = "us-east-1" +access_key = "my-access-key" +secret_key = "my-secret-key" +``` +- In case the Static credentials are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale-gwlb, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.access_key + // secret_key = var.secret_key + } + ``` +- In case the Environment Variables are used, perform modifications described below:
+ a. The next lines in main.tf file, in the provider aws resource, need to be commented: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + b. The next lines in main.tf file, in the provider aws resource, need to be commented for sub-modules /terraform/aws/autoscale, /terraform/aws/management and /terraform/aws/cme-iam-role-gwlb: + ``` + provider "aws" { + // region = var.region + // access_key = var.aws_access_key_ID + // secret_key = var.aws_secret_access_key + } + ``` + +## Usage +- Fill all variables in the /terraform/aws/gwlb/**terraform.tfvars** file with proper values (see below for variables descriptions). +- From a command line initialize the Terraform configuration directory: + ``` + terraform init + ``` +- Create an execution plan: + ``` + terraform plan + ``` + - Create or modify the deployment: + ``` + terraform apply + ``` + + - Variables are configured in /terraform/aws/qs-autoscale/**terraform.tfvars** file as follows: + + ``` + //PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + + // --- VPC Network Configuration --- + vpc_id = "vpc-12345678" + internet_gateway_id ="igw-12345" + availability_zones = ["us-east-1a", "us-east-1b"] + number_of_AZs = 2 + gateways_subnets= ["subnet-123456", "subnet-234567"] + + transit_gateway_attachment_subnet_1_id="subnet-3456" + transit_gateway_attachment_subnet_2_id="subnet-4567" + transit_gateway_attachment_subnet_3_id="subnet-5678" + transit_gateway_attachment_subnet_4_id="subnet-6789" + + nat_gw_subnet_1_cidr ="10.0.13.0/24" + nat_gw_subnet_2_cidr = "10.0.23.0/24" + nat_gw_subnet_3_cidr = "10.0.33.0/24" + nat_gw_subnet_4_cidr = "10.0.43.0/24" + + gwlbe_subnet_1_cidr = "10.0.14.0/24" + gwlbe_subnet_2_cidr = "10.0.24.0/24" + gwlbe_subnet_3_cidr = "10.0.34.0/24" + gwlbe_subnet_4_cidr = "10.0.44.0/24" + + + // --- General Settings --- + key_name = "publickey" + enable_volume_encryption = true + volume_size = 100 + enable_instance_connect = false + disable_instance_termination = false + allow_upload_download = true + management_server = "CP-Management-gwlb-tf" + configuration_template = "gwlb-configuration" + admin_shell = "/etc/cli.sh" + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = "gwlb1" + target_group_name = "tg1" + connection_acceptance_required = "false" + enable_cross_zone_load_balancing = "true" + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = "Check-Point-GW-tf" + gateway_instance_type = "c5.xlarge" + minimum_group_size = 2 + maximum_group_size = 10 + gateway_version = "R81.20-BYOL" + gateway_password_hash = "" + gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. + gateway_SICKey = "12345678" + gateways_provision_address_type = "private" + allocate_public_IP = false + enable_cloudwatch = false + gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = true + management_instance_type = "m5.xlarge" + management_version = "R81.20-BYOL" + management_password_hash = "" + management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. + gateways_policy = "Standard" + gateway_management = "Locally managed" + admin_cidr = "" + gateways_addresses = "" + + // --- Other parameters --- + VolumeType = "gp3" + + + ``` + +- Conditional creation + - To enable cloudwatch for tgw-gwlb: + ``` + enable_cloudwatch = true + ``` + Note: enabling cloudwatch will automatically create IAM role with cloudwatch:PutMetricData permission + - To deploy Security Management Server: + ``` + management_deploy = true + ``` +- To tear down your resources: + ``` + terraform destroy + ``` + +## Inputs +| Name | Description | Type | Allowed values | Default | Required | +|-------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------|----------| +| vpc_id | Select an existing VPC | string | n/a | n/a | yes | +| internet_gateway_id | VPC's Internet Gateway Id | string | n/a | n/a | yes | +| availability_zones | The Availability Zones (AZs) to use for the subnets in the VPC. | string | n/a | n/a | yes | +| Number_of_AZs | Number of Availability Zones to use in the VPC. | number | n/a | 2 | yes | +| Gateways_subnets | Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_1_id | The TGW attachment subnet ID located in the 1st Availability Zone | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_2_id | The TGW attachment subnet ID located in the 2st Availability Zone | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_3_id | The TGW attachment subnet ID located in the 3st Availability Zone | string | n/a | n/a | yes | +| transit_gateway_attachment_subnet_4_id | The TGW attachment subnet ID located in the 4st Availability Zone | string | n/a | n/a | yes | +| nat_gw_subnet_1_cidr | CIDR block for NAT subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.13.0/24 | yes | +| nat_gw_subnet_2_cidr | CIDR block for NAT subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.23.0/24 | yes | +| nat_gw_subnet_3_cidr | CIDR block for NAT subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.33.0/24 | yes | +| nat_gw_subnet_4_cidr | CIDR block for NAT subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.43.0/24 | yes | +| gwlbe_subnet_1_cidr | CIDR block for GWLBe subnet 1 located in the 1st Availability Zone | string | n/a | 10.0.14.0/24 | yes | +| gwlbe_subnet_2_cidr | CIDR block for GWLBe subnet 2 located in the 2st Availability Zone | string | n/a | 10.0.24.0/24 | yes | +| gwlbe_subnet_3_cidr | CIDR block for GWLBe subnet 3 located in the 3st Availability Zone | string | n/a | 10.0.34.0/24 | yes | +| gwlbe_subnet_4_cidr | CIDR block for GWLBe subnet 4 located in the 4st Availability Zone | string | n/a | 10.0.44.0/24 | yes | +| key_name | The EC2 Key Pair name to allow SSH access to the instances | string | n/a | n/a | yes | +| enable_volume_encryption | Encrypt Environment instances volume with default AWS KMS key | bool | true/false | true | no | +| management_server | The name that represents the Security Management Server in the automatic provisioning configuration. | string | n/a | CP-Management-gwlb-tf | yes | +| enable_instance_connect | Enable SSH connection over AWS web console. Supporting regions can be found [here](https://aws.amazon.com/about-aws/whats-new/2019/06/introducing-amazon-ec2-instance-connect/) | bool | true/false | false | no | +| disable_instance_termination | Prevents an instance from accidental termination. Note: Once this attribute is true terraform destroy won't work properly | bool | true/false | false | no | +| metadata_imdsv2_required | Set true to deploy the instance with metadata v2 token required | bool | true/false | true | yes | +| volume_size | Instances volume size | number | n/a | 100 | no | +| allow_upload_download | Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point | bool | true/false | true | no | +| configuration_template | The tag is used by the Security Management Server to automatically provision the Security Gateways. Must be up to 12 alphanumeric characters and unique for each Quick Start deployment | string | n/a | gwlb-ter | no | +| admin_shell | Set the admin shell to enable advanced command line configuration | string | - /etc/cli.sh
- /bin/bash
- /bin/csh
- /bin/tcsh | /etc/cli.sh | no | +| gateway_load_balancer_name | Load Balancer name in AWS | string | n/a | gwlb-terraform | yes | +| target_group_name | Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. | string | n/a | tg1-terraform | yes | +| connection_acceptance_required | Indicate whether requests from service consumers to create an endpoint to your service must be accepted. Default is set to false(acceptance not required). | bool | true/false | false | yes | +| enable_cross_zone_load_balancing | Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges. | bool | true/false | true | yes | +| gateway_name | The name tag of the Security Gateway instances. (optional) | string | n/a | gwlb-terraform | yes | +| gateway_instance_type | The instance type of the Security Gateways | string | - c4.large
- c4.xlarge
- c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| c5.xlarge | no | +| gateways_min_group_size | The minimal number of Security Gateways | number | n/a | 2 | no | +| gateways_max_group_size | The maximal number of Security Gateways | number | n/a | 10 | no | +| gateway_version | Gateway version and license | string | - R81.20-BYOL
- R81.20-PAYG-NGTP
- R81.20-PAYG-NGTX
- R82-BYOL
- R82-PAYG-NGTP
- R82-PAYG-NGTX | R81.20-BYOL | no | +| gateway_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateway_SICKey | The Secure Internal Communication key for trusted connection between Check Point components. Choose a random string consisting of at least 8 alphanumeric characters | string | n/a | "12345678" | yes | +| enable_cloudwatch | Report Check Point specific CloudWatch metrics | bool | true/false | false | no | +| gateway_bootstrap_script | (Optional) An optional script with semicolon (;) separated commands to run on the initial boot | string | n/a | "" | no | +| gateways_provision_address_type | Determines if the gateways are provisioned using their private or public address. | string | - private
- public | private | no | +| allocate_public_IP | Allocate a Public IP for gateway members. | bool | true/false | false | no | +| management_deploy | Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section | bool | true/false | true | no | +| management_instance_type | The EC2 instance type of the Security Management Server | string | - c5.large
- c5.xlarge
- c5.2xlarge
- c5.4xlarge
- c5.9xlarge
- c5.12xlarge
- c5.18xlarge
- c5.24xlarge
- c5n.large
- c5n.xlarge
- c5n.2xlarge
- c5n.4xlarge
- c5n.9xlarge
- c5n.18xlarge
- c5d.large
- c5d.xlarge
- c5d.2xlarge
- c5d.4xlarge
- c5d.9xlarge
- c5d.12xlarge
- c5d.18xlarge
- c5d.24xlarge
- m5.large
- m5.xlarge
- m5.2xlarge
- m5.4xlarge
- m5.8xlarge
- m5.12xlarge
- m5.16xlarge
- m5.24xlarge
- m6i.large
- m6i.xlarge
- m6i.2xlarge
- m6i.4xlarge
- m6i.8xlarge
- m6i.12xlarge
- m6i.16xlarge
- m6i.24xlarge
- m6i.32xlarge
- c6i.large
- c6i.xlarge
- c6i.2xlarge
- c6i.4xlarge
- c6i.8xlarge
- c6i.12xlarge
- c6i.16xlarge
- c6i.24xlarge
- c6i.32xlarge
- c6in.large
- c6in.xlarge
- c6in.2xlarge
- c6in.4xlarge
- c6in.8xlarge
- c6in.12xlarge
- c6in.16xlarge
- c6in.24xlarge
- c6in.32xlarge
- r5.large
- r5.xlarge
- r5.2xlarge
- r5.4xlarge
- r5.8xlarge
- r5.12xlarge
- r5.16xlarge
- r5.24xlarge
- r5a.large
- r5a.xlarge
- r5a.2xlarge
- r5a.4xlarge
- r5a.8xlarge
- r5a.12xlarge
- r5a.16xlarge
- r5a.24xlarge
- r5b.large
- r5b.xlarge
- r5b.2xlarge
- r5b.4xlarge
- r5b.8xlarge
- r5b.12xlarge
- r5b.16xlarge
- r5b.24xlarge
- r5n.large
- r5n.xlarge
- r5n.2xlarge
- r5n.4xlarge
- r5n.8xlarge
- r5n.12xlarge
- r5n.16xlarge
- r5n.24xlarge
- r6i.large
- r6i.xlarge
- r6i.2xlarge
- r6i.4xlarge
- r6i.8xlarge
- r6i.12xlarge
- r6i.16xlarge
- r6i.24xlarge
- r6i.32xlarge
- m6a.large
- m6a.xlarge
- m6a.2xlarge
- m6a.4xlarge
- m6a.8xlarge
- m6a.12xlarge
- m6a.16xlarge
- m6a.24xlarge - m6a.32xlarge
- m6a.48xlarge
| m5.xlarge | no | +| management_version | The license to install on the Security Management Server | string | - R81-BYOL
- R81-PAYG
- R81.10-BYOL
- R81.10-PAYG
- R81.20-BYOL
- R81.20-PAYG
- R82-BYOL
- R82-PAYG | R81.20-BYOL | no | +| management_password_hash | (Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash) | string | n/a | "" | no | +| gateways_policy | The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group | string | n/a | Standard | no | +| gateway_management | Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address. | string | - Locally managed
- Over the internet | Locally managed | no | +| admin_cidr | (CIDR) Allow web, ssh, and graphical clients only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| gateway_addresses | (CIDR) Allow gateways only from this network to communicate with the Management Server | string | valid CIDR | n/a | no | +| volume_type | General Purpose SSD Volume Type | string | - gp3
- gp2 | gp3 | no | +| gateway_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | +| management_maintenance_mode_password_hash | Check Point recommends setting Admin user's password and maintenance-mode password for recovery purposes. For R81.10 and below the Admin user's password is used also as maintenance-mode password. (To generate a password hash use the command "grub2-mkpasswd-pbkdf2" on Linux and paste it here). (optional) | string | n/a | "" | no | + + +## Outputs +| Name | Description | +|---------------------|---------------------------------------------------------------------------------------| +| managment_public_ip | The deployed Security Management AWS instance public IP | +| load_balancer_url | The URL of the external Load Balancer | +| template_name | Name of a gateway configuration template in the automatic provisioning configuration. | +| controller_name | The controller name in CME. | +| gwlb_name | The name of the deployed Gateway Load Balancer | +| gwlb_service_name | The service name for the deployed Gateway Load Balancer | +| gwlb_arn | The arn for the deployed Gateway Load Balancer | + + + +## Revision History +In order to check the template version, please refer to [sk116585](https://supportcenter.checkpoint.com/supportcenter/portal?eventSubmit_doGoviewsolutiondetails=&solutionid=sk116585) + +| Template Version | Description | +|------------------|--------------------------------------------------------------------------------------------------------------------| +| 20240704 | R80.40 version deprecation | +| 20240310 | Add support for requiring use instance metadata service version 2 (IMDSv2) only | +| 20231012 | Update AWS Terraform provider version to 5.20.1 | +| 20230923 | Add support for C5d instance type | +| 20230914 | Add support for maintenance mode password | +| 20230910 | Add bootstrap script execution option for deployed gateways | +| 20230829 | Change default Check Point version to R81.20 | +| 20230806 | Add support for c6in instance type | +| 20221226 | Support ASG Launch Template instead of Launch Configuration | +| 20221123 | R81.20 version support | +| 20220606 | New instance type support | +| 20220414 | First release of Check Point CloudGuard Network Gateway Load Balancer for Transit Gateway Terraform module for AWS | + +## License + +This project is licensed under the MIT License - see the [LICENSE](../../LICENSE) file for details diff --git a/deprecated/terraform/aws/R81/tgw-gwlb/locals.tf b/deprecated/terraform/aws/R81/tgw-gwlb/locals.tf new file mode 100755 index 00000000..0693df6d --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb/locals.tf @@ -0,0 +1,60 @@ +locals { + + regex_valid_gateway_sic_key = "^[a-zA-Z0-9]{8,}$" + // Will fail if var.gateway_SIC_Key is invalid + regex_gateway_sic_result = regex(local.regex_valid_gateway_sic_key, var.gateway_SICKey) == var.gateway_SICKey ? 0 : "Variable [gateway_SIC_Key] must be at least 8 alphanumeric characters" + + control_over_public_or_private_allowed_values = [ + "public", + "private"] + // will fail if [var.control_gateway_over_public_or_private_address] is invalid: + validate_control_over_public_or_private = index(local.control_over_public_or_private_allowed_values, var.gateways_provision_address_type) + + gateway_management_allowed_values = [ + "Locally managed", + "Over the internet"] + // will fail if [var.gateway_management] is invalid: + validate_gateway_management = index(local.gateway_management_allowed_values, var.gateway_management) + + regex_valid_key_name = "[\\S\\s]+[\\S]+" + // will fail if var.key_name is invalid + regex_key_name_result=regex(local.regex_valid_key_name, var.key_name) == var.key_name ? 0 : "Variable [key_name] must be a none empty string" + + regex_valid_management_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.management_password_hash is invalid + regex_management_password_hash = regex(local.regex_valid_management_password_hash, var.management_password_hash) == var.management_password_hash ? 0 : "Variable [management_password_hash] must be a valid password hash" + regex_management_maintenance_mode_password_hash = regex(local.regex_valid_management_password_hash, var.management_maintenance_mode_password_hash) == var.management_maintenance_mode_password_hash ? 0 : "Variable [management_maintenance_mode_password_hash] must be a valid password hash" + + regex_valid_gateway_password_hash = "^[\\$\\./a-zA-Z0-9]*$" + // Will fail if var.gateway_password_hash is invalid + regex_gateway_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_password_hash) == var.gateway_password_hash ? 0 : "Variable [gateway_password_hash] must be a valid password hash" + regex_gateway_maintenance_mode_password_hash = regex(local.regex_valid_gateway_password_hash, var.gateway_maintenance_mode_password_hash) == var.gateway_maintenance_mode_password_hash ? 0 : "Variable [gateway_maintenance_mode_password_hash] must be a valid password hash" + + + regex_valid_admin_cidr = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.admin_cidr is invalid + regex_admin_cidr = regex(local.regex_valid_admin_cidr, var.admin_cidr) == var.admin_cidr ? 0 : "Variable [admin_cidr] must be a valid CIDR" + + regex_valid_gateways_addresses = "^([0-9]{1,3}\\.){3}[0-9]{1,3}/([0-9]|[1-2][0-9]|3[0-2])$" + // Will fail if var.gateways_addresses is invalid + regex_gateways_addresses = regex(local.regex_valid_gateways_addresses, var.gateways_addresses) == var.gateways_addresses ? 0 : "Variable [gateways_addresses] must be a valid gateways addresses" + + regex_valid_management_server = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.management_server is invalid + regex_management_server = regex(local.regex_valid_management_server, var.management_server) == var.management_server ? 0 : "Variable [management_server] can not be an empty string" + + regex_valid_configuration_template = "^([A-Za-z]([-0-9A-Za-z]{0,61}[0-9A-Za-z])?|)$" + // Will fail if var.configuration_template is invalid + regex_configuration_template = regex(local.regex_valid_configuration_template, var.configuration_template) == var.configuration_template ? 0 : "Variable [configuration_template] can not be an empty string" + + deploy_management_condition = var.management_deploy == true + + volume_type_allowed_values = [ + "gp3", + "gp2"] + // will fail if [var.VolumeType] is invalid: + validate_volume_type = index(local.volume_type_allowed_values, var.volume_type) + + + #note: we need to add validiation for every subnet in masters solution +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-gwlb/main.tf b/deprecated/terraform/aws/R81/tgw-gwlb/main.tf new file mode 100755 index 00000000..64ce7101 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb/main.tf @@ -0,0 +1,438 @@ +provider "aws" { + region = var.region + access_key = var.access_key + secret_key = var.secret_key +} + + +resource "aws_subnet" "gwlbe_subnet1" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 0) + cidr_block = var.gwlbe_subnet_1_cidr + tags = { + Name = "GWLBe subnet 1" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet1_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway1.id + } + tags = { + Name = "GWLBe Subnet 1 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet1_rtb_assoc" { + subnet_id = aws_subnet.gwlbe_subnet1.id + route_table_id = aws_route_table.gwlbe_subnet1_rtb.id +} + + +resource "aws_subnet" "gwlbe_subnet2" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 1) + cidr_block = var.gwlbe_subnet_2_cidr + tags = { + Name = "GWLBe subnet 2" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet2_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway2.id + } + tags = { + Name = "GWLBe Subnet 2 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet2_rtb_assoc" { + subnet_id = aws_subnet.gwlbe_subnet2.id + route_table_id = aws_route_table.gwlbe_subnet2_rtb.id +} + + +resource "aws_subnet" "gwlbe_subnet3" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 2) + cidr_block = var.gwlbe_subnet_3_cidr + tags = { + Name = "GWLBe subnet 3" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet3_rtb" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway3[0].id + } + tags = { + Name = "GWLBe Subnet 3 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet3_rtb_assoc" { + count = var.number_of_AZs >= 3 ? 1 :0 + subnet_id = aws_subnet.gwlbe_subnet3[0].id + route_table_id = aws_route_table.gwlbe_subnet3_rtb[0].id +} + + +resource "aws_subnet" "gwlbe_subnet4" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 3) + cidr_block = var.gwlbe_subnet_4_cidr + tags = { + Name = "GWLBe subnet 4" + Network = "Private" + } +} +resource "aws_route_table" "gwlbe_subnet4_rtb" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + nat_gateway_id = aws_nat_gateway.nat_gateway4[0].id + } + tags = { + Name = "GWLBe Subnet 4 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "gwlbe_subnet4_rtb_assoc" { + count = var.number_of_AZs >= 4 ? 1 :0 + subnet_id = aws_subnet.gwlbe_subnet4[0].id + route_table_id = aws_route_table.gwlbe_subnet4_rtb[0].id +} + + + + +resource "aws_subnet" "nat_gw_subnet1" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 0) + cidr_block = var.nat_gw_subnet_1_cidr + tags = { + Name = "NAT subnet 1" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet1_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 1 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet1_rtb_assoc" { + subnet_id = aws_subnet.nat_gw_subnet1.id + route_table_id = aws_route_table.nat_gw_subnet1_rtb.id +} + +resource "aws_subnet" "nat_gw_subnet2" { + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 1) + cidr_block = var.nat_gw_subnet_2_cidr + tags = { + Name = "NAT subnet 2" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet2_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 2 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet2_rtb_assoc" { + subnet_id = aws_subnet.nat_gw_subnet2.id + route_table_id = aws_route_table.nat_gw_subnet2_rtb.id +} + +resource "aws_subnet" "nat_gw_subnet3" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 2) + cidr_block = var.nat_gw_subnet_3_cidr + tags = { + Name = "NAT subnet 3" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet3_rtb" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 3 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet3_rtb_assoc" { + count = var.number_of_AZs >= 3 ? 1 :0 + subnet_id = aws_subnet.nat_gw_subnet3[0].id + route_table_id = aws_route_table.nat_gw_subnet3_rtb[0].id +} + +resource "aws_subnet" "nat_gw_subnet4" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + availability_zone = element(var.availability_zones, 3) + cidr_block = var.nat_gw_subnet_4_cidr + tags = { + Name = "NAT subnet 4" + Network = "Private" + } +} +resource "aws_route_table" "nat_gw_subnet4_rtb" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + gateway_id = var.internet_gateway_id + } + tags = { + Name = "NAT Subnet 4 Route Table" + Network = "Public" + } +} +resource "aws_route_table_association" "nat_gw_subnet4_rtb_assoc" { + count = var.number_of_AZs >= 4 ? 1 :0 + subnet_id = aws_subnet.nat_gw_subnet4[0].id + route_table_id = aws_route_table.nat_gw_subnet4_rtb[0].id +} + +module "gwlb" { + source = "../gwlb" + providers = { + aws = aws + } + vpc_id = var.vpc_id + subnet_ids = var.gateways_subnets + + // --- General Settings --- + key_name = var.key_name + enable_volume_encryption = var.enable_volume_encryption + volume_size = var.volume_size + enable_instance_connect = var.enable_instance_connect + disable_instance_termination = var.disable_instance_termination + metadata_imdsv2_required = var.metadata_imdsv2_required + allow_upload_download = var.allow_upload_download + management_server = var.management_server + configuration_template = var.configuration_template + admin_shell = var.admin_shell + + // --- Gateway Load Balancer Configuration --- + gateway_load_balancer_name = var.gateway_load_balancer_name + target_group_name = var.target_group_name + connection_acceptance_required = false + enable_cross_zone_load_balancing = var.enable_cross_zone_load_balancing + + // --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + gateway_name = var.gateway_name + gateway_instance_type = var.gateway_instance_type + minimum_group_size = var.minimum_group_size + maximum_group_size = var.maximum_group_size + gateway_version = var.gateway_version + gateway_password_hash = var.gateway_password_hash + gateway_maintenance_mode_password_hash = var.gateway_maintenance_mode_password_hash + gateway_SICKey = var.gateway_SICKey + gateways_provision_address_type = var.gateways_provision_address_type + allocate_public_IP = var.allocate_public_IP + enable_cloudwatch = var.enable_cloudwatch + gateway_bootstrap_script = var.gateway_bootstrap_script + + // --- Check Point CloudGuard IaaS Security Management Server Configuration --- + management_deploy = var.management_deploy + management_instance_type = var.management_instance_type + management_version = var.management_version + management_password_hash = var.management_password_hash + management_maintenance_mode_password_hash = var.management_maintenance_mode_password_hash + gateways_policy = var.gateways_policy + gateway_management = var.gateway_management + admin_cidr = var.admin_cidr + gateways_addresses = var.gateways_addresses + + volume_type = var.volume_type +} + +resource "aws_vpc_endpoint" "gwlb_endpoint1" { + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet1] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet1[*].id + tags = { + "Name" = "gwlb_endpoint1" + } +} +resource "aws_vpc_endpoint" "gwlb_endpoint2" { + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet2] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet2[*].id + tags = { + "Name" = "gwlb_endpoint2" + } +} +resource "aws_vpc_endpoint" "gwlb_endpoint3" { + count = var.number_of_AZs >= 3 ? 1 :0 + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet3] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet3[*].id + tags = { + "Name" = "gwlb_endpoint3" + } +} +resource "aws_vpc_endpoint" "gwlb_endpoint4" { + count = var.number_of_AZs >= 4 ? 1 :0 + depends_on = [module.gwlb, aws_subnet.gwlbe_subnet4] + vpc_id = var.vpc_id + vpc_endpoint_type = "GatewayLoadBalancer" + service_name = module.gwlb.gwlb_service_name + subnet_ids = aws_subnet.gwlbe_subnet4[*].id + tags = { + "Name" = "gwlb_endpoint4" + } +} + + +resource "aws_route_table" "tgw_attachment_subnet1_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint1.id + } + tags = { + Name = "TGW Attachment Subnet 1 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment1_rtb_assoc" { + subnet_id = var.transit_gateway_attachment_subnet_1_id + route_table_id = aws_route_table.tgw_attachment_subnet1_rtb.id +} +resource "aws_route_table" "tgw_attachment_subnet2_rtb" { + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint2.id + } + tags = { + Name = "TGW Attachment Subnet 2 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment2_rtb_assoc" { + subnet_id = var.transit_gateway_attachment_subnet_2_id + route_table_id = aws_route_table.tgw_attachment_subnet2_rtb.id +} +resource "aws_route_table" "tgw_attachment_subnet3_rtb" { + count = var.number_of_AZs >= 3 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint3[0].id + } + tags = { + Name = "TGW Attachment Subnet 3 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment3_rtb_assoc" { + count = var.number_of_AZs >= 3 ? 1 :0 + subnet_id = var.transit_gateway_attachment_subnet_3_id + route_table_id = aws_route_table.tgw_attachment_subnet3_rtb[0].id +} +resource "aws_route_table" "tgw_attachment_subnet4_rtb" { + count = var.number_of_AZs >= 4 ? 1 :0 + vpc_id = var.vpc_id + route{ + cidr_block = "0.0.0.0/0" + vpc_endpoint_id = aws_vpc_endpoint.gwlb_endpoint4[0].id + } + tags = { + Name = "TGW Attachment Subnet 4 Route Table" + Network = "Private" + } +} +resource "aws_route_table_association" "tgw_attachment4_rtb_assoc" { + count = var.number_of_AZs >= 4 ? 1 :0 + subnet_id = var.transit_gateway_attachment_subnet_4_id + route_table_id = aws_route_table.tgw_attachment_subnet4_rtb[0].id +} + + +resource "aws_eip" "nat_gw_public_address1" { +} +resource "aws_eip" "nat_gw_public_address2" { +} +resource "aws_eip" "nat_gw_public_address3" { + count = var.number_of_AZs >= 3 ? 1 : 0 +} +resource "aws_eip" "nat_gw_public_address4" { + count = var.number_of_AZs >= 4 ? 1 : 0 +} + +resource "aws_nat_gateway" "nat_gateway1" { + depends_on = [aws_subnet.nat_gw_subnet1, aws_eip.nat_gw_public_address1] + allocation_id = aws_eip.nat_gw_public_address1.id + subnet_id = aws_subnet.nat_gw_subnet1.id + + tags = { + Name = "NatGW1" + } +} +resource "aws_nat_gateway" "nat_gateway2" { + depends_on = [aws_subnet.nat_gw_subnet2, aws_eip.nat_gw_public_address2] + allocation_id = aws_eip.nat_gw_public_address2.id + subnet_id = aws_subnet.nat_gw_subnet2.id + + tags = { + Name = "NatGW2" + } +} +resource "aws_nat_gateway" "nat_gateway3" { + count = var.number_of_AZs >= 3 ? 1 :0 + depends_on = [aws_subnet.nat_gw_subnet3, aws_eip.nat_gw_public_address3] + allocation_id = aws_eip.nat_gw_public_address3[0].id + subnet_id = aws_subnet.nat_gw_subnet3[0].id + + tags = { + Name = "NatGW3" + } +} +resource "aws_nat_gateway" "nat_gateway4" { + count = var.number_of_AZs >= 4 ? 1 :0 + depends_on = [aws_subnet.nat_gw_subnet4, aws_eip.nat_gw_public_address4] + allocation_id = aws_eip.nat_gw_public_address4[0].id + subnet_id = aws_subnet.nat_gw_subnet4[0].id + + tags = { + Name = "NatGW4" + } +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-gwlb/output.tf b/deprecated/terraform/aws/R81/tgw-gwlb/output.tf new file mode 100755 index 00000000..15cb48a3 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb/output.tf @@ -0,0 +1,24 @@ +output "Deployment" { + value = "Finalizing instances configuration may take up to 20 minutes after deployment is finished." +} +output "management_public_ip" { + depends_on = [module.gwlb] + value = module.gwlb[*].management_public_ip +} +output "gwlb_arn" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_arn +} +output "gwlb_service_name" { + depends_on = [module.gwlb] + value = module.gwlb[*].gwlb_service_name +} +output "gwlb_name" { + value = var.gateway_load_balancer_name +} +output "controller_name" { + value = "gwlb-controller" +} +output "template_name" { + value = var.configuration_template +} \ No newline at end of file diff --git a/deprecated/terraform/aws/R81/tgw-gwlb/terraform.tfvars b/deprecated/terraform/aws/R81/tgw-gwlb/terraform.tfvars new file mode 100755 index 00000000..266b4d1a --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb/terraform.tfvars @@ -0,0 +1,69 @@ +//PLEASE refer to README.md for accepted values FOR THE VARIABLES BELOW + +// --- VPC Network Configuration --- +vpc_id = "vpc-12345678" +internet_gateway_id ="igw-12345" +availability_zones = ["us-east-1a", "us-east-1b"] +number_of_AZs = 2 +gateways_subnets= ["subnet-123456", "subnet-234567"] + +transit_gateway_attachment_subnet_1_id="subnet-3456" +transit_gateway_attachment_subnet_2_id="subnet-4567" +transit_gateway_attachment_subnet_3_id="subnet-5678" +transit_gateway_attachment_subnet_4_id="subnet-6789" + +nat_gw_subnet_1_cidr ="10.0.13.0/24" +nat_gw_subnet_2_cidr = "10.0.23.0/24" +nat_gw_subnet_3_cidr = "10.0.33.0/24" +nat_gw_subnet_4_cidr = "10.0.43.0/24" + +gwlbe_subnet_1_cidr = "10.0.14.0/24" +gwlbe_subnet_2_cidr = "10.0.24.0/24" +gwlbe_subnet_3_cidr = "10.0.34.0/24" +gwlbe_subnet_4_cidr = "10.0.44.0/24" + +// --- General Settings --- +key_name = "publickey" +enable_volume_encryption = true +volume_size = 100 +enable_instance_connect = false +disable_instance_termination = false +metadata_imdsv2_required = true +allow_upload_download = true +management_server = "CP-Management-gwlb-tf" +configuration_template = "gwlb-configuration" +admin_shell = "/etc/cli.sh" + +// --- Gateway Load Balancer Configuration --- +gateway_load_balancer_name = "gwlb1" +target_group_name = "tg1" +enable_cross_zone_load_balancing = "true" + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- +gateway_name = "Check-Point-GW-tf" +gateway_instance_type = "c5.xlarge" +minimum_group_size = 2 +maximum_group_size = 10 +gateway_version = "R81.20-BYOL" +gateway_password_hash = "" +gateway_maintenance_mode_password_hash = "" # For R81.10 and below the gateway_password_hash is used also as maintenance-mode password. +gateway_SICKey = "12345678" +gateways_provision_address_type = "private" +allocate_public_IP = false +enable_cloudwatch = false +gateway_bootstrap_script = "echo 'this is bootstrap script' > /home/admin/bootstrap.txt" + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- +management_deploy = true +management_instance_type = "m5.xlarge" +management_version = "R81.20-BYOL" +management_password_hash = "" +management_maintenance_mode_password_hash = "" # For R81.10 and below the management_password_hash is used also as maintenance-mode password. +gateways_policy = "Standard" +gateway_management = "Locally managed" +admin_cidr = "0.0.0.0/0" +gateways_addresses = "0.0.0.0/0" + +// --- Other parameters --- +volume_type = "gp3" + diff --git a/deprecated/terraform/aws/R81/tgw-gwlb/variables.tf b/deprecated/terraform/aws/R81/tgw-gwlb/variables.tf new file mode 100755 index 00000000..52b97b13 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb/variables.tf @@ -0,0 +1,333 @@ +// Module: Check Point CloudGuard Network Gateway Load Balancer into an existing VPC + +// --- AWS Provider --- +variable "region" { + type = string + description = "AWS region" + default = "" +} +variable "access_key" { + type = string + description = "AWS access key" + default = "" +} +variable "secret_key" { + type = string + description = "AWS secret key" + default = "" +} + +// ---VPC Network Configuration --- +variable "vpc_id" { + type = string +} +variable "internet_gateway_id" { + type = string + description = "VPC's Internet Gateway Id (e.g. igw-123a4567)" +} +variable "availability_zones"{ + type = list(string) + description = "The Availability Zones (AZs) to use for the subnets in the VPC. Select two (the logical order is preserved)" +} +variable "number_of_AZs" { + type = number + description = "Number of Availability Zones to use in the VPC. This must match your selections in the list of Availability Zones parameter" + default = 2 +} +resource "null_resource" "availability_zones_validation1" { + count = var.number_of_AZs == length(var.availability_zones) ? 0 : "variable availability_zones list size must be equal to variable num_of_AZs" +} + +variable "gateways_subnets" { + type = list(string) + description = "Select at least 2 public subnets in the VPC. If you choose to deploy a Security Management Server it will be deployed in the first subnet" +} + +variable "transit_gateway_attachment_subnet_1_id" { + type = string + description = "The TGW attachment subnet ID located in the 1st Availability Zone" +} +variable "transit_gateway_attachment_subnet_2_id" { + type = string + description = "The TGW attachment subnet ID located in the 2st Availability Zone" +} +variable "transit_gateway_attachment_subnet_3_id" { + type = string + description = "The TGW attachment subnet ID located in the 3st Availability Zone" + default = "" +} +variable "transit_gateway_attachment_subnet_4_id" { + type = string + description = "The TGW attachment subnet ID located in the 4st Availability Zone" + default = "" +} +variable "nat_gw_subnet_1_cidr" { + type = string + description = "CIDR block for NAT subnet 1 located in the 1st Availability Zone" + default = "10.0.13.0/24" +} +variable "nat_gw_subnet_2_cidr" { + type = string + description = "CIDR block for NAT subnet 2 located in the 2st Availability Zone" + default = "10.0.23.0/24" +} +variable "nat_gw_subnet_3_cidr" { + type = string + description = "CIDR block for NAT subnet 3 located in the 3st Availability Zone" + default = "10.0.33.0/24" +} +variable "nat_gw_subnet_4_cidr" { + type = string + description = "CIDR block for NAT subnet 4 located in the 4st Availability Zone" + default = "10.0.43.0/24" +} +variable "gwlbe_subnet_1_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 1 located in the 1st Availability Zone" + default = "10.0.14.0/24" +} +variable "gwlbe_subnet_2_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 2 located in the 2st Availability Zone" + default = "10.0.24.0/24" +} +variable "gwlbe_subnet_3_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 3 located in the 3st Availability Zone" + default = "10.0.34.0/24" +} +variable "gwlbe_subnet_4_cidr" { + type = string + description = "CIDR block for Gateway Loadbalancer endpoint subnet 4 located in the 4st Availability Zone" + default = "10.0.44.0/24" +} +// --- General Settings --- +variable "key_name" { + type = string + description = "The EC2 Key Pair name to allow SSH access to the instances" +} +variable "enable_volume_encryption" { + type = bool + description = "Encrypt Environment instances volume with default AWS KMS key" + default = true +} +variable "volume_size" { + type = number + description = "Root volume size (GB) - minimum 100" + default = 100 +} +resource "null_resource" "volume_size_too_small" { + // Will fail if var.volume_size is less than 100 + count = var.volume_size >= 100 ? 0 : "variable volume_size must be at least 100" +} +variable "volume_type" { + type = string + description = "General Purpose SSD Volume Type" + default = "gp3" +} +variable "enable_instance_connect" { + type = bool + description = "Enable SSH connection over AWS web console" + default = false +} +variable "disable_instance_termination" { + type = bool + description = "Prevents an instance from accidental termination" + default = false +} +variable "metadata_imdsv2_required" { + type = bool + description = "Set true to deploy the instance with metadata v2 token required" + default = true +} +variable "allow_upload_download" { + type = bool + description = "Automatically download Blade Contracts and other important data. Improve product experience by sending data to Check Point" + default = true +} +variable "management_server" { + type = string + description = "The name that represents the Security Management Server in the automatic provisioning configuration." + default = "gwlb-management-server" +} +variable "configuration_template" { + type = string + description = "A name of a gateway configuration template in the automatic provisioning configuration." + default = "gwlb-ASG-configuration" + validation { + condition = length(var.configuration_template) < 31 + error_message = "The configuration_template name can not exceed 30 characters" + } +} +variable "admin_shell" { + type = string + description = "Set the admin shell to enable advanced command line configuration" + default = "/etc/cli.sh" +} + +// --- Gateway Load Balancer Configuration --- + +variable "gateway_load_balancer_name" { + type = string + description = "Gateway Load Balancer name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "gwlb1" +} +resource "null_resource" "gateway_load_balancer_name_too_long" { + // Will fail if gateway_load_balancer_name more than 32 + count = length(var.gateway_load_balancer_name) <= 32 ? 0 : "variable gateway_load_balancer_name must be at most 32" +} +variable "target_group_name" { + type = string + description = "Target Group Name. This name must be unique within your AWS account and can have a maximum of 32 alphanumeric characters and hyphens. A name cannot begin or end with a hyphen." + default = "tg1" +} +resource "null_resource" "target_group_name_too_long" { + // Will fail if target_group_name more than 32 + count = length(var.target_group_name) <= 32 ? 0 : "variable target_group_name must be at most 32" +} +variable "enable_cross_zone_load_balancing" { + type = bool + description = "Select 'true' to enable cross-az load balancing. NOTE! this may cause a spike in cross-az charges." + default = true +} + +// --- Check Point CloudGuard IaaS Security Gateways Auto Scaling Group Configuration --- + +variable "gateway_name" { + type = string + description = "The name tag of the Security Gateway instances. (optional)" + default = "Check-Point-Gateway-tf" +} +variable "gateway_instance_type" { + type = string + description = "The EC2 instance type for the Security Gateways." + default = "c5.xlarge" +} +module "validate_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "gateway" + instance_type = var.gateway_instance_type +} +variable "minimum_group_size" { + type = number + description = "The minimal number of Security Gateways." + default = 2 +} +variable "maximum_group_size" { + type = number + description = "The maximal number of Security Gateways." + default = 10 +} +variable "gateway_version" { + type = string + description = "The version and license to install on the Security Gateways." + default = "R81.20-BYOL" +} +module "validate_gateway_version" { + source = "../modules/common/version_license" + + chkp_type = "gwlb_gw" + version_license = var.gateway_version +} +variable "gateway_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" +} +variable "gateway_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the gateway instances, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateway_SICKey" { + type = string + description = "The Secure Internal Communication key for trusted connection between Check Point components (at least 8 alphanumeric characters)" +} + +variable "gateways_provision_address_type" { + type = string + description = "Determines if the gateways are provisioned using their private or public address" + default = "private" +} + +variable "allocate_public_IP" { + type = bool + description = "Allocate an Elastic IP for security gateway." + default = false +} + +resource "null_resource" "invalid_allocation" { + // Will fail if var.gateways_provision_address_type is public and var.allocate_public_IP is false + count = var.gateways_provision_address_type != "public" ? 0 : var.allocate_public_IP == true ? 0 : "Gateway's selected to be provisioned by public IP, but [allocate_public_IP] parameter is false" +} + +variable "enable_cloudwatch" { + type = bool + description = "Report Check Point specific CloudWatch metrics." + default = false +} + +variable "gateway_bootstrap_script" { + type = string + description = "(Optional) An optional script with semicolon (;) separated commands to run on the initial boot" + default = "" +} + +// --- Check Point CloudGuard IaaS Security Management Server Configuration --- + +variable "management_deploy" { + type = bool + description = "Select 'false' to use an existing Security Management Server or to deploy one later and to ignore the other parameters of this section" + default = true +} +variable "management_instance_type" { + type = string + description = "The EC2 instance type of the Security Management Server" + default = "m5.xlarge" +} +module "validate_management_instance_type" { + source = "../modules/common/instance_type" + + chkp_type = "management" + instance_type = var.management_instance_type +} +variable "management_version" { + type = string + description = "The license to install on the Security Management Server" + default = "R81.20-BYOL" +} +module "validate_management_version" { + source = "../modules/common/version_license" + + chkp_type = "management" + version_license = var.management_version +} +variable "management_password_hash" { + type = string + description = "(Optional) Admin user's password hash (use command 'openssl passwd -6 PASSWORD' to get the PASSWORD's hash)" + default = "" +} +variable "management_maintenance_mode_password_hash" { + description = "Maintenance mode password hash for the management instance, relevant only for R81.20 and higher versions" + type = string + default = "" +} +variable "gateways_policy" { + type = string + description = "The name of the Security Policy package to be installed on the gateways in the Security Gateways Auto Scaling group" + default = "Standard" +} +variable "gateway_management" { + type = string + description = "Select 'Over the internet' if any of the gateways you wish to manage are not directly accessed via their private IP address." + default = "Locally managed" +} +variable "admin_cidr" { + type = string + description = "Allow web, ssh, and graphical clients only from this network to communicate with the Security Management Server" +} +variable "gateways_addresses" { + type = string + description = "Allow gateways only from this network to communicate with the Security Management Server" +} + diff --git a/deprecated/terraform/aws/R81/tgw-gwlb/versions.tf b/deprecated/terraform/aws/R81/tgw-gwlb/versions.tf new file mode 100755 index 00000000..dbebf275 --- /dev/null +++ b/deprecated/terraform/aws/R81/tgw-gwlb/versions.tf @@ -0,0 +1,15 @@ +terraform { + required_version = ">= 0.14.3" + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.20.0" + } + http = { + version = "~> 3.4.0" + } + random = { + version = "~> 3.5.1" + } + } +}