diff --git a/infrastructure/terraform/.gitignore b/infrastructure/terraform/.gitignore index f0d9138a..579b6414 100644 --- a/infrastructure/terraform/.gitignore +++ b/infrastructure/terraform/.gitignore @@ -3,6 +3,13 @@ # Transient backends components/**/backend_tfscaffold.tf +# Exclude all .tfvars files, which are likely to contain sensitive data, such as +# password, private keys, and other secrets. These should not be part of version +# control as they are data points which are potentially sensitive and subject +# to change depending on the environment. +*.tfvars +*.tfvars.json + # Compiled files **/*.tfstate **/*.tfplan diff --git a/infrastructure/terraform/README b/infrastructure/terraform/README new file mode 100644 index 00000000..838d1775 --- /dev/null +++ b/infrastructure/terraform/README @@ -0,0 +1,3 @@ +This is an implementation of https://github.com/tfutils/tfscaffold for NHS Notify + +Update the `etc/global.tfvars` file according to your NHS Notify Domain, and follow https://github.com/tfutils/tfscaffold?tab=readme-ov-file#bootstrapping to get your tfstate s3 bucket set up diff --git a/infrastructure/terraform/components/acct/.terraform-version b/infrastructure/terraform/components/acct/.terraform-version new file mode 100644 index 00000000..631f7908 --- /dev/null +++ b/infrastructure/terraform/components/acct/.terraform-version @@ -0,0 +1 @@ +latest:^1\.8\. diff --git a/infrastructure/terraform/components/acct/README b/infrastructure/terraform/components/acct/README new file mode 100644 index 00000000..d2148877 --- /dev/null +++ b/infrastructure/terraform/components/acct/README @@ -0,0 +1,5 @@ +README for 'acct' component - Account-level resources + +This component is intended to be run to set up things (such as a DNS subdomain) at the account level, and this should be run for each account belonging to the Notify Domain - i.e. there should be a nonprod and prod environment .tfvars + +Copy the `env_eu-west-2_example.tfvars` file in the `etc` directory and adjust as needed for nonprod and prod for your NHS Notify Domain. diff --git a/infrastructure/terraform/components/acct/locals_tfscaffold.tf b/infrastructure/terraform/components/acct/locals_tfscaffold.tf new file mode 100644 index 00000000..e5084cdf --- /dev/null +++ b/infrastructure/terraform/components/acct/locals_tfscaffold.tf @@ -0,0 +1,45 @@ +locals { + terraform_state_bucket = format( + "%s-tfscaffold-%s-%s", + var.project, + var.aws_account_id, + var.region, + ) + + csi = replace( + format( + "%s-%s-%s", + var.project, + var.environment, + var.component, + ), + "_", + "", + ) + + # CSI for use in resources with a global namespace, i.e. S3 Buckets + csi_global = replace( + format( + "%s-%s-%s-%s-%s", + var.project, + var.aws_account_id, + var.region, + var.environment, + var.component, + ), + "_", + "", + ) + + default_tags = merge( + var.default_tags, + { + Project = var.project + Environment = var.environment + Component = var.component + Group = var.group + NHSNotifyDomain = var.nhs_notify_domain + Name = local.csi + }, + ) +} diff --git a/infrastructure/terraform/components/acct/outputs.tf b/infrastructure/terraform/components/acct/outputs.tf new file mode 100644 index 00000000..5bc34180 --- /dev/null +++ b/infrastructure/terraform/components/acct/outputs.tf @@ -0,0 +1,19 @@ +output "aws_account_id" { + value = var.aws_account_id +} + +output "r53_delegation_set_id" { + value = aws_route53_delegation_set.main.id +} + +output "r53_delegation_set_nameservers" { + value = aws_route53_delegation_set.main.name_servers +} + +output "r53_subdomain_name" { + value = var.subdomain_name +} + +output "r53_subdomain_id" { + value = one(aws_route53_zone.subdomain[*].id) +} diff --git a/infrastructure/terraform/components/acct/provider_aws.tf b/infrastructure/terraform/components/acct/provider_aws.tf new file mode 100644 index 00000000..a8058431 --- /dev/null +++ b/infrastructure/terraform/components/acct/provider_aws.tf @@ -0,0 +1,18 @@ +provider "aws" { + region = var.region + + allowed_account_ids = [ + var.aws_account_id, + ] + + default_tags { + tags = { + Project = var.project + Environment = var.environment + Component = var.component + Group = var.group + NHSNotifyDomain = var.nhs_notify_domain + Name = local.csi + } + } +} diff --git a/infrastructure/terraform/components/acct/route53_delegation_set_main.tf b/infrastructure/terraform/components/acct/route53_delegation_set_main.tf new file mode 100644 index 00000000..76ad88e0 --- /dev/null +++ b/infrastructure/terraform/components/acct/route53_delegation_set_main.tf @@ -0,0 +1,3 @@ +resource "aws_route53_delegation_set" "main" { + reference_name = "main" +} diff --git a/infrastructure/terraform/components/acct/route53_zone_subdomain.tf b/infrastructure/terraform/components/acct/route53_zone_subdomain.tf new file mode 100644 index 00000000..cc52061b --- /dev/null +++ b/infrastructure/terraform/components/acct/route53_zone_subdomain.tf @@ -0,0 +1,7 @@ +resource "aws_route53_zone" "subdomain" { + count = var.subdomain_name != "" ? 1 : 0 + + name = var.subdomain_name + + delegation_set_id = aws_route53_delegation_set.main.id +} diff --git a/infrastructure/terraform/components/acct/variables.tf b/infrastructure/terraform/components/acct/variables.tf new file mode 100644 index 00000000..f625501d --- /dev/null +++ b/infrastructure/terraform/components/acct/variables.tf @@ -0,0 +1,64 @@ +## +# Basic Required Variables for tfscaffold Components +## + +variable "project" { + type = string + description = "The name of the tfscaffold project" +} + +variable "environment" { + type = string + description = "The name of the tfscaffold environment" +} + +variable "aws_account_id" { + type = string + description = "The AWS Account ID (numeric)" +} + +variable "region" { + type = string + description = "The AWS Region" +} + +variable "group" { + type = string + description = "The group variables are being inherited from (often synonmous with account short-name)" +} + +## +# tfscaffold variables specific to this component +## + +# This is the only primary variable to have its value defined as +# a default within its declaration in this file, because the variables +# purpose is as an identifier unique to this component, rather +# then to the environment from where all other variables come. +variable "component" { + type = string + description = "The variable encapsulating the name of this component" + default = "acct" +} + +variable "nhs_notify_domain" { + type = string + description = "The name of the NHS Notify Domain that this is deploying to" +} + +variable "default_tags" { + type = map(string) + description = "A map of default tags to apply to all taggable resources within the component" + default = {} +} + + +## +# Variables specific to the "acct" component +## + +variable "subdomain_name" { + type = string + description = "The subdomain name to create a Route53 zone for" + default = "" +} diff --git a/infrastructure/terraform/components/acct/versions.tf b/infrastructure/terraform/components/acct/versions.tf new file mode 100644 index 00000000..ee15bad7 --- /dev/null +++ b/infrastructure/terraform/components/acct/versions.tf @@ -0,0 +1,10 @@ +terraform { + required_providers { + aws = { + source = "hashicorp/aws" + version = "~> 5.50" + } + } + + required_version = "~> 1.8.4" +} diff --git a/infrastructure/terraform/etc/.gitkeep b/infrastructure/terraform/etc/.gitkeep deleted file mode 100644 index e69de29b..00000000