test implementation

This commit is contained in:
matthieu42morin 2024-03-01 03:33:04 +01:00
parent a37b687e81
commit 021a5b336a
16 changed files with 595 additions and 0 deletions

28
main.tf Normal file
View File

@ -0,0 +1,28 @@
module "vpc-secrets" {
source = "./modules/vpc-secrets"
version = "1.0.0"
resource_name_prefix = var.resource_name_prefix
}
module "vault-starter" {
source = "hashicorp/vault-starter/aws"
version = "1.0.0"
vpc_id = var.vpc_id
allowed_inbound_cidrs_lb = var.allowed_inbound_cidrs_lb
allowed_inbound_cidrs_ssh = var.allowed_inbound_cidrs_ssh
vault_version = var.vault_version
leader_tls_servername = var.leader_tls_servername
node_count = var.node_count
kms_key_deletion_window = var.kms_key_deletion_window
user_supplied_iam_role_name = var.user_supplied_iam_role_name
user_supplied_ami_id = var.user_supplied_ami_id
user_supplied_kms_key_arn = var.user_supplied_kms_key_arn
user_supplied_userdata_path = var.user_supplied_userdata_path
lb_certificate_arn = var.lb_certificate_arn
lb_type = var.lb_type
lb_health_check_path = var.lb_health_check_path
resource_name_prefix = var.resource_name_prefix
secrets_manager_arn = var.secrets_manager_arn
private_subnet_tags = var.private_subnet_ids
instance_type = var.instance_type
ssl_policy = var.ssl_policy
}

View File

@ -0,0 +1,33 @@
# EXAMPLE: Prerequisite Configuration (VPC and Secrets)
## About This Example
In order to deploy the Vault module, you must have an AWS VPC that
meets the requirements [listed in the main
README](../../README.md#how-to-use-this-module) along with TLS certs that can be
used with the Vault nodes and load balancer. If you do not already have these
resources, you can use the code provided in this directory to provision them.
## How to Use This Module
1. Ensure your AWS credentials are [configured
correctly](https://docs.aws.amazon.com/cli/latest/userguide/cli-configure-files.html)
2. Configure required (and optional if desired) variables
3. Run `terraform init` and `terraform apply`
## Required variables
* `resource_name_prefix` - string value to use as base for resource names
## Note
- The default AWS region is `us-east-1` (as specified by the `aws_region`
variable). You may change this if wish to deploy Vault elsewhere, but please
be sure to change the value for the `azs` variable as well and specify the
appropriate availability zones for your new region.
### Security Note:
- The [Terraform State](https://www.terraform.io/docs/language/state/index.html)
produced by this code has sensitive data (cert private keys) stored in it.
Please secure your Terraform state using the [recommendations listed
here](https://www.terraform.io/docs/language/state/sensitive-data.html#recommendations).

View File

@ -0,0 +1,21 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
module "vpc" {
source = "terraform-aws-modules/vpc/aws"
version = "3.0.0"
name = "${var.resource_name_prefix}-vault"
cidr = var.vpc_cidr
azs = var.azs
enable_nat_gateway = true
one_nat_gateway_per_az = true
private_subnets = var.private_subnet_cidrs
public_subnets = var.public_subnet_cidrs
tags = var.common_tags
}

View File

@ -0,0 +1,17 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
output "private_subnet_ids" {
description = "Private subnet IDs"
value = module.vpc.private_subnets
}
output "vpc_id" {
description = "The ID of the VPC"
value = module.vpc.vpc_id
}

View File

@ -0,0 +1,48 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
variable "azs" {
description = "availability zones to use in AWS region"
type = list(string)
}
variable "common_tags" {
type = map(string)
description = "Tags for VPC resources"
}
variable "resource_name_prefix" {
description = "Prefix for resource names (e.g. \"prod\")"
type = string
}
variable "private_subnet_cidrs" {
description = "CIDR blocks for private subnets"
type = list(string)
default = [
"10.0.0.0/19",
"10.0.32.0/19",
"10.0.64.0/19",
]
}
variable "public_subnet_cidrs" {
description = "CIDR blocks for public subnets"
type = list(string)
default = [
"10.0.128.0/20",
"10.0.144.0/20",
"10.0.160.0/20",
]
}
variable "vpc_cidr" {
description = "CIDR block for VPC"
type = string
default = "10.0.0.0/16"
}

View File

@ -0,0 +1,25 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
provider "aws" {
region = var.aws_region
}
module "vpc" {
source = "./aws-vpc/"
azs = var.azs
common_tags = var.tags
resource_name_prefix = var.resource_name_prefix
}
module "secrets" {
source = "./secrets/"
resource_name_prefix = var.resource_name_prefix
}

View File

@ -0,0 +1,32 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
output "lb_certificate_arn" {
description = "ARN of ACM cert to use with Vault LB listener"
value = module.secrets.lb_certificate_arn
}
output "leader_tls_servername" {
description = "Shared SAN that will be given to the Vault nodes configuration for use as leader_tls_servername"
value = module.secrets.leader_tls_servername
}
output "private_subnet_ids" {
description = "Private subnet IDs"
value = module.vpc.private_subnet_ids
}
output "secrets_manager_arn" {
description = "ARN of secrets_manager secret"
value = module.secrets.secrets_manager_arn
}
output "vpc_id" {
description = "The ID of the VPC"
value = module.vpc.vpc_id
}

View File

@ -0,0 +1,12 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
resource "aws_acm_certificate" "vault" {
private_key = tls_private_key.server.private_key_pem
certificate_body = tls_locally_signed_cert.server.cert_pem
certificate_chain = tls_self_signed_cert.ca.cert_pem
}

View File

@ -0,0 +1,20 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
resource "aws_secretsmanager_secret" "tls" {
name = "${var.resource_name_prefix}-tls-secret"
description = "contains TLS certs and private keys"
kms_key_id = var.kms_key_id
recovery_window_in_days = var.recovery_window
tags = var.tags
}
resource "aws_secretsmanager_secret_version" "tls" {
secret_id = aws_secretsmanager_secret.tls.id
secret_string = local.secret
}

View File

@ -0,0 +1,21 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
output "lb_certificate_arn" {
description = "ARN of ACM cert to use with Vault LB listener"
value = aws_acm_certificate.vault.arn
}
output "leader_tls_servername" {
description = "Shared SAN that will be given to the Vault nodes configuration for use as leader_tls_servername"
value = var.shared_san
}
output "secrets_manager_arn" {
description = "ARN of secrets_manager secret"
value = aws_secretsmanager_secret.tls.arn
}

View File

@ -0,0 +1,95 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
# Generate a private key so you can create a CA cert with it.
resource "tls_private_key" "ca" {
algorithm = "RSA"
rsa_bits = 2048
}
# Create a CA cert with the private key you just generated.
resource "tls_self_signed_cert" "ca" {
private_key_pem = tls_private_key.ca.private_key_pem
subject {
common_name = "ca.vault.server.com"
}
validity_period_hours = 720 # 30 days
allowed_uses = [
"cert_signing",
"crl_signing",
]
is_ca_certificate = true
# provisioner "local-exec" {
# command = "echo '${tls_self_signed_cert.ca.cert_pem}' > ./vault-ca.pem"
# }
}
# Generate another private key. This one will be used
# To create the certs on your Vault nodes
resource "tls_private_key" "server" {
algorithm = "RSA"
rsa_bits = 2048
# provisioner "local-exec" {
# command = "echo '${tls_private_key.server.private_key_pem}' > ./vault-key.pem"
# }
}
resource "tls_cert_request" "server" {
private_key_pem = tls_private_key.server.private_key_pem
subject {
common_name = "vault.server.com"
}
dns_names = [
var.shared_san,
"localhost",
]
ip_addresses = [
"127.0.0.1",
]
}
resource "tls_locally_signed_cert" "server" {
cert_request_pem = tls_cert_request.server.cert_request_pem
ca_private_key_pem = tls_private_key.ca.private_key_pem
ca_cert_pem = tls_self_signed_cert.ca.cert_pem
validity_period_hours = 720 # 30 days
allowed_uses = [
"client_auth",
"digital_signature",
"key_agreement",
"key_encipherment",
"server_auth",
]
# provisioner "local-exec" {
# command = "echo '${tls_locally_signed_cert.server.cert_pem}' > ./vault-crt.pem"
# }
}
locals {
tls_data = {
vault_ca = base64encode(tls_self_signed_cert.ca.cert_pem)
vault_cert = base64encode(tls_locally_signed_cert.server.cert_pem)
vault_pk = base64encode(tls_private_key.server.private_key_pem)
}
}
locals {
secret = jsonencode(local.tls_data)
}

View File

@ -0,0 +1,39 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
variable "kms_key_id" {
type = string
description = "Specifies the ARN or ID of the AWS KMS customer master key (CMK) to be used to encrypt the secret values in the versions stored in this secret. If you don't specify this value, then Secrets Manager defaults to using the AWS account's default CMK (the one named aws/secretsmanager"
default = null
}
variable "recovery_window" {
type = number
description = "Specifies the number of days that AWS Secrets Manager waits before it can delete the secret"
default = 0
}
variable "resource_name_prefix" {
type = string
description = "Prefix for resource names (e.g. \"prod\")"
}
# variable related to TLS cert generation
variable "shared_san" {
type = string
description = "This is a shared server name that the certs for all Vault nodes contain. This is the same value you will supply as input to the Vault installation module for the leader_tls_servername variable."
default = "vault.server.com"
}
variable "tags" {
type = map(string)
description = "Tags for secrets manager secret"
default = {
Vault = "tls-data"
}
}

View File

@ -0,0 +1,32 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
variable "aws_region" {
description = "AWS region to deploy resources into"
type = string
default = "eu-north-1"
}
variable "azs" {
description = "availability zones to use in AWS region"
type = list(string)
default = [
"eu-north-1a",
"eu-north-1b",
]
}
variable "tags" {
type = map(string)
description = "Tags for VPC resources"
default = {}
}
variable "resource_name_prefix" {
description = "Prefix for resource names in VPC infrastructure"
}

View File

@ -0,0 +1,15 @@
/**
* Copyright © 2014-2022 HashiCorp, Inc.
*
* This Source Code is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this project, you can obtain one at http://mozilla.org/MPL/2.0/.
*
*/
terraform {
required_version = ">= 1.2.1"
required_providers {
aws = ">= 3.0.0, < 4.0.0"
tls = ">= 3.0.0, < 4.0.0"
}
}

13
providers.tf Normal file
View File

@ -0,0 +1,13 @@
terraform {
required_version = ">= 1.0"
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.38.0"
}
}
}
provider "aws" {
region = var.aws_region
profile = var.aws_profile
}

144
variables.tf Normal file
View File

@ -0,0 +1,144 @@
# === General ===
variable "resource_name_prefix" {
type = string
description = "Resource name prefix used for tagging and naming AWS resources"
}
variable "vault_version" {
type = string
description = "Vault version"
default = "1.15.5"
}
variable "aws_region" {
type = string
description = "AWS region where Vault will be deployed"
default = "eu-north-1"
}
variable "aws_profile" {
type = string
description = "The AWS Profile to use for this project."
default = "tf_dev"
}
# === config ===
variable "ami_id" {
type = string
description = "The AMI ID to use for Vault instances"
default = "value"
}
variable "instance_type" {
type = string
description = "The instance type to use for Vault nodes"
default = "t3.micro"
}
variable "lb_type" {
description = "The type of load balancer to provision: network or application."
type = string
}
variable "node_count" {
type = number
description = "Number of Vault nodes to deploy in ASG"
default = 2
}
# === Certs ===
variable "ssl_policy" {
type = string
description = "The SSL policy to use for the load balancer"
default = "ELBSecurityPolicy-TLS-1-2-2017-01"
}
variable "secrets_manager_arn" {
type = string
description = "Secrets manager ARN where TLS cert info is stored"
}
variable "leader_tls_servername" {
type = string
description = "One of the shared DNS SAN used to create the certs use for mTLS"
}
variable "lb_certificate_arn" {
type = string
description = "ARN of TLS certificate imported into ACM for use with LB listener"
}
variable "kms_key_deletion_window" {
type = number
description = "The duration in days after which the key is deleted after destruction of the resource"
default = 7
}
variable "lb_health_check_path" {
type = string
description = "The path to use for the health check"
default = "/v1/sys/health"
}
# === VPC ===
variable "allowed_inbound_cidrs_lb" {
type = list(string)
description = "CIDR blocks to allow inbound traffic to the load balancer"
default = ["0.0.0.0/0"]
}
variable "allowed_inbound_cidrs_ssh" {
type = list(string)
description = "CIDR blocks to allow inbound SSH traffic to the Vault instances"
default = ["0.0.0.0/0"]
}
variable "vpc_id" {
type = string
description = "VPC ID where Vault will be deployed"
}
variable "private_subnet_ids" {
type = list(string)
description = "Subnet IDs to deploy Vault into"
}
# === user supplied variables ===
variable "user_supplied_ami_id" {
type = string
description = "(Optional) User-provided AMI ID to use with Vault instances. If you provide this value, please ensure it will work with the default userdata script (assumes latest version of Ubuntu LTS). Otherwise, please provide your own userdata script using the user_supplied_userdata_path variable."
default = null
}
variable "user_supplied_iam_role_name" {
type = string
description = "(Optional) User-provided IAM role name. This will be used for the instance profile provided to the AWS launch configuration. The minimum permissions must match the defaults generated by the IAM submodule for cloud auto-join and auto-unseal."
default = null
}
variable "user_supplied_kms_key_arn" {
type = string
description = "(Optional) User-provided KMS key ARN. Providing this will disable the KMS submodule from generating a KMS key used for Vault auto-unseal"
default = null
}
variable "user_supplied_userdata_path" {
type = string
description = "(Optional) File path to custom userdata script being supplied by the user"
default = null
}