save
This commit is contained in:
parent
67ac803045
commit
2441364269
|
@ -6,6 +6,9 @@
|
|||
*.tfstate
|
||||
*.tfstate.*
|
||||
|
||||
# Backend config public ignore
|
||||
backend.hcl
|
||||
|
||||
# Crash log files
|
||||
crash.log
|
||||
crash.*.log
|
||||
|
@ -33,22 +36,3 @@ override.tf.json
|
|||
# Ignore CLI configuration files
|
||||
.terraformrc
|
||||
terraform.rc
|
||||
|
||||
# ---> Ansible
|
||||
*.retry
|
||||
|
||||
# ---> Linux
|
||||
*~
|
||||
|
||||
# temporary files which can be created if a process still has a handle open of a deleted file
|
||||
.fuse_hidden*
|
||||
|
||||
# KDE directory preferences
|
||||
.directory
|
||||
|
||||
# Linux trash folder which might appear on any partition or disk
|
||||
.Trash-*
|
||||
|
||||
# .nfs files are created when an open file is removed but is still being accessed
|
||||
.nfs*
|
||||
|
||||
|
|
|
@ -0,0 +1,45 @@
|
|||
# This file is maintained automatically by "terraform init".
|
||||
# Manual edits may be lost in future updates.
|
||||
|
||||
provider "registry.terraform.io/hashicorp/aws" {
|
||||
version = "5.39.0"
|
||||
constraints = ">= 3.0.0, >= 3.15.0, >= 4.0.0"
|
||||
hashes = [
|
||||
"h1:isoOv/JipnnPD3j8Df6XwGU1i4egjlygrgBv0RfsZ7g=",
|
||||
"zh:01e405306470ed784bc9d38dbaeff394bd2c0f7d58e5592c5d0165c87d84e4b0",
|
||||
"zh:0328fbd42a91e50601318d2c364a80ebd3b4e5755c85df6fafd2fed80bc54598",
|
||||
"zh:042420e08d1ef1e2ed51c394539a6db27e031bedb9eaa19db9ccaf9fa93b9b36",
|
||||
"zh:47dee460b2c06676e16f5070fff71e5e9eb24b74bcd7b4f7b53eea8ebd3c972f",
|
||||
"zh:49c34f21a05bf5150e3a0a87c997fcd831ae81e3f2df86191e2fdd231525b585",
|
||||
"zh:4d5a98726216e260296bdc13e562179a743ef4738b65154da697c2d9e9eb5c9b",
|
||||
"zh:7fb08af13c868d8d20519b373eeb6707a0cea078495123e28e71727993474f53",
|
||||
"zh:9b12af85486a96aedd8d7984b0ff811a4b42e3d88dad1a3fb4c0b580d04fa425",
|
||||
"zh:a57e7e44f79991e55be02f2b147a433b5a2690188be0510409b79e9b00e37009",
|
||||
"zh:aeeb120cd6245f67ae3e52e13005c2dc1f091787564dd6b39ee6c05b2c239c53",
|
||||
"zh:b5d39c6e55d0355f9fd93a802355166bd27edaf9acb753b190562474447674b2",
|
||||
"zh:cfcc1922b380db5f90fd5ffc1e49fb9f316e6c41de4603f65b05d20ace72e15e",
|
||||
"zh:d221d8cea09229743d2647944c0420a8e9e5d7e3ff088b30cbce85a8b051dcab",
|
||||
"zh:dccca0239df6d39686b0f0947040b3c0e1270a4bab268c402b742cf5a7759296",
|
||||
"zh:ef0564fb70e8210db9bf472f662e093a1a1f204a1c1cb46467231be1a78882f3",
|
||||
]
|
||||
}
|
||||
|
||||
provider "registry.terraform.io/hashicorp/tls" {
|
||||
version = "4.0.5"
|
||||
constraints = ">= 3.0.0"
|
||||
hashes = [
|
||||
"h1:gthwVUwv0WLGMwx7GR/N6XyIONzrSJJaXD6dDJB4FlY=",
|
||||
"zh:01cfb11cb74654c003f6d4e32bbef8f5969ee2856394a96d127da4949c65153e",
|
||||
"zh:0472ea1574026aa1e8ca82bb6df2c40cd0478e9336b7a8a64e652119a2fa4f32",
|
||||
"zh:1a8ddba2b1550c5d02003ea5d6cdda2eef6870ece86c5619f33edd699c9dc14b",
|
||||
"zh:1e3bb505c000adb12cdf60af5b08f0ed68bc3955b0d4d4a126db5ca4d429eb4a",
|
||||
"zh:6636401b2463c25e03e68a6b786acf91a311c78444b1dc4f97c539f9f78de22a",
|
||||
"zh:76858f9d8b460e7b2a338c477671d07286b0d287fd2d2e3214030ae8f61dd56e",
|
||||
"zh:a13b69fb43cb8746793b3069c4d897bb18f454290b496f19d03c3387d1c9a2dc",
|
||||
"zh:a90ca81bb9bb509063b736842250ecff0f886a91baae8de65c8430168001dad9",
|
||||
"zh:c4de401395936e41234f1956ebadbd2ed9f414e6908f27d578614aaa529870d4",
|
||||
"zh:c657e121af8fde19964482997f0de2d5173217274f6997e16389e7707ed8ece8",
|
||||
"zh:d68b07a67fbd604c38ec9733069fbf23441436fecf554de6c75c032f82e1ef19",
|
||||
"zh:f569b65999264a9416862bca5cd2a6177d94ccb0424f3a4ef424428912b9cb3c",
|
||||
]
|
||||
}
|
27
main.tf
27
main.tf
|
@ -1,20 +1,20 @@
|
|||
module "vpc-secrets" {
|
||||
source = "./modules/vpc-secrets"
|
||||
module "networking" {
|
||||
source = "./modules/networking"
|
||||
azs = var.azs
|
||||
shared_san = var.shared_san
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
}
|
||||
module "vault-starter" {
|
||||
source = "hashicorp/vault-starter/aws"
|
||||
version = "1.0.0"
|
||||
source = "./modules/matts-vault-starter"
|
||||
|
||||
vault_version = var.vault_version
|
||||
node_count = var.node_count
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
instance_type = var.instance_type
|
||||
|
||||
# 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
|
||||
# user_supplied_userdata_path = var.user_supplied_userdata_path
|
||||
|
||||
lb_type = var.lb_type
|
||||
lb_health_check_path = var.lb_health_check_path
|
||||
|
@ -24,13 +24,12 @@ module "vault-starter" {
|
|||
kms_key_deletion_window = var.kms_key_deletion_window
|
||||
ssl_policy = var.ssl_policy
|
||||
|
||||
# === Supplied by ./modules/vpc-secrets ===
|
||||
depends_on = [module.vpc-secrets]
|
||||
|
||||
private_subnet_tags = module.vpc-secrets.private_subnet_ids
|
||||
secrets_manager_arn = module.vpc-secrets.secrets_manager_arn
|
||||
vpc_id = module.vpc-secrets.vpc_id
|
||||
lb_certificate_arn = module.vpc-secrets.lb_certificate_arn
|
||||
leader_tls_servername = module.vpc-secrets.leader_tls_servername
|
||||
# === Supplied by ./modules/networking ===
|
||||
depends_on = [module.networking]
|
||||
|
||||
private_subnet_ids = module.networking.private_subnet_ids
|
||||
secrets_manager_arn = module.networking.secrets_manager_arn
|
||||
vpc_id = module.networking.vpc_id
|
||||
lb_certificate_arn = module.networking.lb_certificate_arn
|
||||
leader_tls_servername = module.networking.leader_tls_servername
|
||||
}
|
|
@ -0,0 +1,89 @@
|
|||
/**
|
||||
* 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/.
|
||||
*
|
||||
*/
|
||||
|
||||
data "aws_region" "current" {}
|
||||
|
||||
module "iam" {
|
||||
source = "./modules/iam"
|
||||
|
||||
aws_region = data.aws_region.current.name
|
||||
kms_key_arn = module.kms.kms_key_arn
|
||||
permissions_boundary = var.permissions_boundary
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
secrets_manager_arn = var.secrets_manager_arn
|
||||
user_supplied_iam_role_name = var.user_supplied_iam_role_name
|
||||
}
|
||||
|
||||
module "kms" {
|
||||
source = "./modules/kms"
|
||||
|
||||
common_tags = var.common_tags
|
||||
kms_key_deletion_window = var.kms_key_deletion_window
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
user_supplied_kms_key_arn = var.user_supplied_kms_key_arn
|
||||
}
|
||||
|
||||
module "loadbalancer" {
|
||||
source = "./modules/load_balancer"
|
||||
|
||||
allowed_inbound_cidrs = var.allowed_inbound_cidrs_lb
|
||||
common_tags = var.common_tags
|
||||
lb_certificate_arn = var.lb_certificate_arn
|
||||
lb_deregistration_delay = var.lb_deregistration_delay
|
||||
lb_health_check_path = var.lb_health_check_path
|
||||
lb_subnets = var.private_subnet_ids
|
||||
lb_type = var.lb_type
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
ssl_policy = var.ssl_policy
|
||||
vault_sg_id = module.vm.vault_sg_id
|
||||
vpc_id = module.networking.vpc_id
|
||||
}
|
||||
|
||||
module "networking" {
|
||||
source = "./modules/networking"
|
||||
|
||||
vpc_id = var.vpc_id
|
||||
}
|
||||
|
||||
module "user_data" {
|
||||
source = "./modules/user_data"
|
||||
|
||||
aws_region = data.aws_region.current.name
|
||||
kms_key_arn = module.kms.kms_key_arn
|
||||
leader_tls_servername = var.leader_tls_servername
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
secrets_manager_arn = var.secrets_manager_arn
|
||||
user_supplied_userdata_path = var.user_supplied_userdata_path
|
||||
vault_version = var.vault_version
|
||||
}
|
||||
|
||||
locals {
|
||||
vault_target_group_arns = concat(
|
||||
[module.loadbalancer.vault_target_group_arn],
|
||||
var.additional_lb_target_groups,
|
||||
)
|
||||
}
|
||||
|
||||
module "vm" {
|
||||
source = "./modules/vm"
|
||||
|
||||
allowed_inbound_cidrs = var.allowed_inbound_cidrs_lb
|
||||
allowed_inbound_cidrs_ssh = var.allowed_inbound_cidrs_ssh
|
||||
aws_iam_instance_profile = module.iam.aws_iam_instance_profile
|
||||
common_tags = var.common_tags
|
||||
instance_type = var.instance_type
|
||||
key_name = var.key_name
|
||||
lb_type = var.lb_type
|
||||
node_count = var.node_count
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
userdata_script = module.user_data.vault_userdata_base64_encoded
|
||||
user_supplied_ami_id = var.user_supplied_ami_id
|
||||
vault_lb_sg_id = module.loadbalancer.vault_lb_sg_id
|
||||
vault_subnets = var.private_subnet_ids
|
||||
vault_target_group_arns = local.vault_target_group_arns
|
||||
vpc_id = module.networking.vpc_id
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
# AWS IAM Module
|
||||
|
||||
## Required variables
|
||||
|
||||
* `aws_region` - Specific AWS region being used
|
||||
* `kms_key_arn` - KMS Key ARN used for Vault auto-unseal permissions
|
||||
* `resource_name_prefix` - Resource name prefix used for tagging and naming AWS resources
|
||||
* `secrets_manager_arn` - Secrets manager ARN where TLS cert info is stored
|
||||
|
||||
## Example usage
|
||||
|
||||
```hcl
|
||||
module "iam" {
|
||||
source = "./modules/iam"
|
||||
|
||||
aws_region = data.aws_region.current.name
|
||||
kms_key_arn = var.kms_key_arn
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
secrets_manager_arn = var.secrets_manager_arn
|
||||
}
|
||||
```
|
|
@ -0,0 +1,120 @@
|
|||
/**
|
||||
* 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_iam_instance_profile" "vault" {
|
||||
name_prefix = "${var.resource_name_prefix}-vault"
|
||||
role = var.user_supplied_iam_role_name != null ? var.user_supplied_iam_role_name : aws_iam_role.instance_role[0].name
|
||||
}
|
||||
|
||||
resource "aws_iam_role" "instance_role" {
|
||||
count = var.user_supplied_iam_role_name != null ? 0 : 1
|
||||
name_prefix = "${var.resource_name_prefix}-vault"
|
||||
permissions_boundary = var.permissions_boundary
|
||||
assume_role_policy = data.aws_iam_policy_document.instance_role.json
|
||||
}
|
||||
|
||||
data "aws_iam_policy_document" "instance_role" {
|
||||
statement {
|
||||
effect = "Allow"
|
||||
actions = [
|
||||
"sts:AssumeRole",
|
||||
]
|
||||
|
||||
principals {
|
||||
type = "Service"
|
||||
identifiers = ["ec2.amazonaws.com"]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
resource "aws_iam_role_policy" "cloud_auto_join" {
|
||||
count = var.user_supplied_iam_role_name != null ? 0 : 1
|
||||
name = "${var.resource_name_prefix}-vault-auto-join"
|
||||
role = aws_iam_role.instance_role[0].id
|
||||
policy = data.aws_iam_policy_document.cloud_auto_join.json
|
||||
}
|
||||
|
||||
data "aws_iam_policy_document" "cloud_auto_join" {
|
||||
statement {
|
||||
effect = "Allow"
|
||||
|
||||
actions = [
|
||||
"ec2:DescribeInstances",
|
||||
]
|
||||
|
||||
resources = ["*"]
|
||||
}
|
||||
}
|
||||
|
||||
resource "aws_iam_role_policy" "auto_unseal" {
|
||||
count = var.user_supplied_iam_role_name != null ? 0 : 1
|
||||
name = "${var.resource_name_prefix}-vault-auto-unseal"
|
||||
role = aws_iam_role.instance_role[0].id
|
||||
policy = data.aws_iam_policy_document.auto_unseal.json
|
||||
}
|
||||
|
||||
data "aws_iam_policy_document" "auto_unseal" {
|
||||
statement {
|
||||
effect = "Allow"
|
||||
|
||||
actions = [
|
||||
"kms:DescribeKey",
|
||||
"kms:Encrypt",
|
||||
"kms:Decrypt",
|
||||
]
|
||||
|
||||
resources = [
|
||||
var.kms_key_arn,
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
resource "aws_iam_role_policy" "session_manager" {
|
||||
count = var.user_supplied_iam_role_name != null ? 0 : 1
|
||||
name = "${var.resource_name_prefix}-vault-ssm"
|
||||
role = aws_iam_role.instance_role[0].id
|
||||
policy = data.aws_iam_policy_document.session_manager.json
|
||||
}
|
||||
|
||||
data "aws_iam_policy_document" "session_manager" {
|
||||
statement {
|
||||
effect = "Allow"
|
||||
|
||||
actions = [
|
||||
"ssm:UpdateInstanceInformation",
|
||||
"ssmmessages:CreateControlChannel",
|
||||
"ssmmessages:CreateDataChannel",
|
||||
"ssmmessages:OpenControlChannel",
|
||||
"ssmmessages:OpenDataChannel"
|
||||
]
|
||||
|
||||
resources = [
|
||||
"*",
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
resource "aws_iam_role_policy" "secrets_manager" {
|
||||
count = var.user_supplied_iam_role_name != null ? 0 : 1
|
||||
name = "${var.resource_name_prefix}-vault-secrets-manager"
|
||||
role = aws_iam_role.instance_role[0].id
|
||||
policy = data.aws_iam_policy_document.secrets_manager.json
|
||||
}
|
||||
|
||||
data "aws_iam_policy_document" "secrets_manager" {
|
||||
statement {
|
||||
effect = "Allow"
|
||||
|
||||
actions = [
|
||||
"secretsmanager:GetSecretValue",
|
||||
]
|
||||
|
||||
resources = [
|
||||
var.secrets_manager_arn,
|
||||
]
|
||||
}
|
||||
}
|
|
@ -0,0 +1,10 @@
|
|||
/**
|
||||
* 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 "aws_iam_instance_profile" {
|
||||
value = aws_iam_instance_profile.vault.name
|
||||
}
|
|
@ -0,0 +1,38 @@
|
|||
/**
|
||||
* 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" {
|
||||
type = string
|
||||
description = "Specific AWS region being used"
|
||||
}
|
||||
|
||||
variable "kms_key_arn" {
|
||||
type = string
|
||||
description = "KMS Key ARN used for Vault auto-unseal permissions"
|
||||
}
|
||||
|
||||
variable "permissions_boundary" {
|
||||
description = "(Optional) IAM Managed Policy to serve as permissions boundary for IAM Role"
|
||||
type = string
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
}
|
||||
|
||||
variable "secrets_manager_arn" {
|
||||
type = string
|
||||
description = "Secrets manager ARN where TLS cert info is stored"
|
||||
}
|
||||
|
||||
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
|
||||
}
|
|
@ -0,0 +1,17 @@
|
|||
# AWS KMS Module
|
||||
|
||||
## Required variables
|
||||
|
||||
* `kms_key_deletion_window` - Duration in days after which the key is deleted after destruction of the resource (must be between 7 and 30 days)
|
||||
* `resource_name_prefix` - Resource name prefix used for tagging and naming AWS resources
|
||||
|
||||
## Example usage
|
||||
|
||||
```hcl
|
||||
module "kms" {
|
||||
source = "./modules/kms"
|
||||
|
||||
kms_key_deletion_window = var.kms_key_deletion_window
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
}
|
||||
```
|
|
@ -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_kms_key" "vault" {
|
||||
count = var.user_supplied_kms_key_arn != null ? 0 : 1
|
||||
deletion_window_in_days = var.kms_key_deletion_window
|
||||
description = "AWS KMS Customer-managed key used for Vault auto-unseal and encryption"
|
||||
enable_key_rotation = false
|
||||
is_enabled = true
|
||||
key_usage = "ENCRYPT_DECRYPT"
|
||||
|
||||
tags = merge(
|
||||
{ Name = "${var.resource_name_prefix}-vault-key" },
|
||||
var.common_tags,
|
||||
)
|
||||
}
|
|
@ -0,0 +1,10 @@
|
|||
/**
|
||||
* 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 "kms_key_arn" {
|
||||
value = var.user_supplied_kms_key_arn != null ? var.user_supplied_kms_key_arn : aws_kms_key.vault[0].arn
|
||||
}
|
|
@ -0,0 +1,28 @@
|
|||
/**
|
||||
* 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 "common_tags" {
|
||||
type = map(string)
|
||||
description = "(Optional) Map of common tags for all taggable AWS resources."
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "kms_key_deletion_window" {
|
||||
type = number
|
||||
description = "Duration in days after which the key is deleted after destruction of the resource (must be between 7 and 30 days)."
|
||||
}
|
||||
|
||||
variable "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
}
|
||||
|
||||
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
|
||||
}
|
|
@ -0,0 +1,29 @@
|
|||
# AWS Load Balancer Module
|
||||
|
||||
## Required variables
|
||||
|
||||
* `lb_certificate_arn` - ARN of TLS certificate imported into ACM for use with LB listener
|
||||
* `lb_health_check_path` - The endpoint to check for Vault's health status
|
||||
* `lb_subnets` - Subnets where load balancer will be deployed
|
||||
* `lb_type` - The type of load balancer to provision: network or application
|
||||
* `resource_name_prefix` - Resource name prefix used for tagging and naming AWS resources
|
||||
* `ssl_policy` - SSL policy to use on LB listener
|
||||
* `vault_sg_id` - Security group ID of Vault cluster
|
||||
* `vpc_id` - VPC ID where Vault will be deployed
|
||||
|
||||
## Example usage
|
||||
|
||||
```hcl
|
||||
module "loadbalancer" {
|
||||
source = "./modules/load_balancer"
|
||||
|
||||
lb_certificate_arn = var.lb_certificate_arn
|
||||
lb_health_check_path = var.lb_health_check_path
|
||||
lb_subnets = var.vault_subnet_ids
|
||||
lb_type = var.lb_type
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
ssl_policy = var.ssl_policy
|
||||
vault_sg_id = var.vault_sg_id
|
||||
vpc_id = var.vpc_id
|
||||
}
|
||||
```
|
|
@ -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/.
|
||||
*
|
||||
*/
|
||||
|
||||
resource "aws_security_group" "vault_lb" {
|
||||
count = var.lb_type == "application" ? 1 : 0
|
||||
description = "Security group for the application load balancer"
|
||||
name = "${var.resource_name_prefix}-vault-lb-sg"
|
||||
vpc_id = var.vpc_id
|
||||
|
||||
tags = merge(
|
||||
{ Name = "${var.resource_name_prefix}-vault-lb-sg" },
|
||||
var.common_tags,
|
||||
)
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_lb_inbound" {
|
||||
count = var.lb_type == "application" && var.allowed_inbound_cidrs != null ? 1 : 0
|
||||
description = "Allow specified CIDRs access to load balancer on port 8200"
|
||||
security_group_id = aws_security_group.vault_lb[0].id
|
||||
type = "ingress"
|
||||
from_port = 8200
|
||||
to_port = 8200
|
||||
protocol = "tcp"
|
||||
cidr_blocks = var.allowed_inbound_cidrs
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_lb_outbound" {
|
||||
count = var.lb_type == "application" ? 1 : 0
|
||||
description = "Allow outbound traffic from load balancer to Vault nodes on port 8200"
|
||||
security_group_id = aws_security_group.vault_lb[0].id
|
||||
type = "egress"
|
||||
from_port = 8200
|
||||
to_port = 8200
|
||||
protocol = "tcp"
|
||||
source_security_group_id = var.vault_sg_id
|
||||
}
|
||||
|
||||
locals {
|
||||
lb_security_groups = var.lb_type == "network" ? null : [aws_security_group.vault_lb[0].id]
|
||||
lb_protocol = var.lb_type == "network" ? "TCP" : "HTTPS"
|
||||
}
|
||||
|
||||
resource "aws_lb" "vault_lb" {
|
||||
name = "${var.resource_name_prefix}-vault-lb"
|
||||
internal = true
|
||||
load_balancer_type = var.lb_type
|
||||
subnets = var.lb_subnets
|
||||
security_groups = local.lb_security_groups
|
||||
drop_invalid_header_fields = var.lb_type == "application" ? true : null
|
||||
|
||||
tags = merge(
|
||||
{ Name = "${var.resource_name_prefix}-vault-lb" },
|
||||
var.common_tags,
|
||||
)
|
||||
}
|
||||
|
||||
resource "aws_lb_target_group" "vault" {
|
||||
name = "${var.resource_name_prefix}-vault-tg"
|
||||
deregistration_delay = var.lb_deregistration_delay
|
||||
target_type = "instance"
|
||||
port = 8200
|
||||
protocol = local.lb_protocol
|
||||
vpc_id = var.vpc_id
|
||||
|
||||
health_check {
|
||||
healthy_threshold = 2
|
||||
unhealthy_threshold = 2
|
||||
protocol = "HTTPS"
|
||||
port = "traffic-port"
|
||||
path = var.lb_health_check_path
|
||||
interval = 30
|
||||
}
|
||||
|
||||
tags = merge(
|
||||
{ Name = "${var.resource_name_prefix}-vault-tg" },
|
||||
var.common_tags,
|
||||
)
|
||||
}
|
||||
|
||||
resource "aws_lb_listener" "vault" {
|
||||
load_balancer_arn = aws_lb.vault_lb.id
|
||||
port = 8200
|
||||
protocol = local.lb_protocol
|
||||
ssl_policy = local.lb_protocol == "HTTPS" ? var.ssl_policy : null
|
||||
certificate_arn = local.lb_protocol == "HTTPS" ? var.lb_certificate_arn : null
|
||||
|
||||
default_action {
|
||||
type = "forward"
|
||||
target_group_arn = aws_lb_target_group.vault.arn
|
||||
}
|
||||
}
|
|
@ -0,0 +1,31 @@
|
|||
/**
|
||||
* 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 "vault_lb_arn" {
|
||||
description = "ARN of Vault load balancer"
|
||||
value = aws_lb.vault_lb.arn
|
||||
}
|
||||
|
||||
output "vault_lb_dns_name" {
|
||||
description = "DNS name of Vault load balancer"
|
||||
value = aws_lb.vault_lb.dns_name
|
||||
}
|
||||
|
||||
output "vault_lb_sg_id" {
|
||||
description = "Security group ID of Vault load balancer"
|
||||
value = var.lb_type == "application" ? aws_security_group.vault_lb[0].id : null
|
||||
}
|
||||
|
||||
output "vault_lb_zone_id" {
|
||||
description = "Zone ID of Vault load balancer"
|
||||
value = aws_lb.vault_lb.zone_id
|
||||
}
|
||||
|
||||
output "vault_target_group_arn" {
|
||||
description = "Target group ARN to register Vault nodes with"
|
||||
value = aws_lb_target_group.vault.arn
|
||||
}
|
|
@ -0,0 +1,64 @@
|
|||
/**
|
||||
* 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 "allowed_inbound_cidrs" {
|
||||
type = list(string)
|
||||
description = "List of CIDR blocks to permit inbound traffic from to load balancer"
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "common_tags" {
|
||||
type = map(string)
|
||||
description = "(Optional) Map of common tags for all taggable AWS resources."
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "lb_certificate_arn" {
|
||||
type = string
|
||||
description = "ARN of TLS certificate imported into ACM for use with LB listener"
|
||||
}
|
||||
|
||||
variable "lb_deregistration_delay" {
|
||||
type = string
|
||||
description = "Amount time, in seconds, for Vault LB target group to wait before changing the state of a deregistering target from draining to unused."
|
||||
default = 300
|
||||
}
|
||||
|
||||
variable "lb_health_check_path" {
|
||||
type = string
|
||||
description = "The endpoint to check for Vault's health status."
|
||||
}
|
||||
|
||||
variable "lb_subnets" {
|
||||
type = list(string)
|
||||
description = "Subnets where load balancer will be deployed"
|
||||
}
|
||||
|
||||
variable "lb_type" {
|
||||
description = "The type of load balancer to provison: network or application."
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
}
|
||||
|
||||
variable "ssl_policy" {
|
||||
type = string
|
||||
description = "SSL policy to use on LB listener"
|
||||
}
|
||||
|
||||
variable "vault_sg_id" {
|
||||
type = string
|
||||
description = "Security group ID of Vault cluster"
|
||||
}
|
||||
|
||||
variable "vpc_id" {
|
||||
type = string
|
||||
description = "VPC ID where Vault will be deployed"
|
||||
}
|
|
@ -0,0 +1,15 @@
|
|||
# AWS Networking Module
|
||||
|
||||
## Required variables
|
||||
|
||||
* `vpc_id` - VPC ID where Vault will be deployed
|
||||
|
||||
## Example usage
|
||||
|
||||
```hcl
|
||||
module "networking" {
|
||||
source = "./modules/networking"
|
||||
|
||||
vpc_id = var.vpc_id
|
||||
}
|
||||
```
|
|
@ -0,0 +1,10 @@
|
|||
/**
|
||||
* 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/.
|
||||
*
|
||||
*/
|
||||
|
||||
data "aws_vpc" "selected" {
|
||||
id = var.vpc_id
|
||||
}
|
|
@ -0,0 +1,10 @@
|
|||
/**
|
||||
* 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 "vpc_id" {
|
||||
value = data.aws_vpc.selected.id
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
/**
|
||||
* 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 "vpc_id" {
|
||||
type = string
|
||||
description = "VPC ID where Vault will be deployed"
|
||||
}
|
|
@ -0,0 +1,25 @@
|
|||
# AWS User Data Module
|
||||
|
||||
## Required variables
|
||||
|
||||
* `aws_region` - AWS region where Vault is being deployed
|
||||
* `kms_key_arn` - KMS Key ARN used for Vault auto-unseal
|
||||
* `leader_tls_servername` - One of the shared DNS SAN used to create the certs use for mTLS
|
||||
* `resource_name_prefix` - Resource name prefix used for tagging and naming AWS resources
|
||||
* `secrets_manager_arn` - Secrets manager ARN where TLS cert info is stored
|
||||
* `vault_version` - Vault version
|
||||
|
||||
## Example usage
|
||||
|
||||
```hcl
|
||||
module "user_data" {
|
||||
source = "./modules/user_data"
|
||||
|
||||
aws_region = data.aws_region.current.name
|
||||
kms_key_arn = var.kms_key_arn
|
||||
leader_tls_servername = var.leader_tls_servername
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
secrets_manager_arn = var.secrets_manager_arn
|
||||
vault_version = var.vault_version
|
||||
}
|
||||
```
|
|
@ -0,0 +1,22 @@
|
|||
/**
|
||||
* 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/.
|
||||
*
|
||||
*/
|
||||
|
||||
locals {
|
||||
vault_user_data = base64encode(
|
||||
templatefile(
|
||||
"${path.module}/templates/install_vault.sh.tpl",
|
||||
{
|
||||
region = var.aws_region
|
||||
name = var.resource_name_prefix
|
||||
vault_version = var.vault_version
|
||||
kms_key_arn = var.kms_key_arn
|
||||
secrets_manager_arn = var.secrets_manager_arn
|
||||
leader_tls_servername = var.leader_tls_servername
|
||||
}
|
||||
)
|
||||
)
|
||||
}
|
|
@ -0,0 +1,10 @@
|
|||
/**
|
||||
* 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 "vault_userdata_base64_encoded" {
|
||||
value = base64encode(local.vault_user_data)
|
||||
}
|
|
@ -0,0 +1,83 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
imds_token=$( curl -Ss -H "X-aws-ec2-metadata-token-ttl-seconds: 30" -XPUT 169.254.169.254/latest/api/token )
|
||||
instance_id=$( curl -Ss -H "X-aws-ec2-metadata-token: $imds_token" 169.254.169.254/latest/meta-data/instance-id )
|
||||
local_ipv4=$( curl -Ss -H "X-aws-ec2-metadata-token: $imds_token" 169.254.169.254/latest/meta-data/local-ipv4 )
|
||||
|
||||
# install package
|
||||
|
||||
curl -fsSL https://apt.releases.hashicorp.com/gpg | apt-key add -
|
||||
apt-add-repository "deb [arch=amd64] https://apt.releases.hashicorp.com $(lsb_release -cs) main"
|
||||
apt-get update
|
||||
apt-get install -y vault=${vault_version}-* awscli jq
|
||||
|
||||
echo "Configuring system time"
|
||||
timedatectl set-timezone UTC
|
||||
|
||||
# removing any default installation files from /opt/vault/tls/
|
||||
rm -rf /opt/vault/tls/*
|
||||
|
||||
# /opt/vault/tls should be readable by all users of the system
|
||||
chmod 0755 /opt/vault/tls
|
||||
|
||||
# vault-key.pem should be readable by the vault group only
|
||||
touch /opt/vault/tls/vault-key.pem
|
||||
chown root:vault /opt/vault/tls/vault-key.pem
|
||||
chmod 0640 /opt/vault/tls/vault-key.pem
|
||||
|
||||
secret_result=$(aws secretsmanager get-secret-value --secret-id ${secrets_manager_arn} --region ${region} --output text --query SecretString)
|
||||
|
||||
jq -r .vault_cert <<< "$secret_result" | base64 -d > /opt/vault/tls/vault-cert.pem
|
||||
|
||||
jq -r .vault_ca <<< "$secret_result" | base64 -d > /opt/vault/tls/vault-ca.pem
|
||||
|
||||
jq -r .vault_pk <<< "$secret_result" | base64 -d > /opt/vault/tls/vault-key.pem
|
||||
|
||||
cat << EOF > /etc/vault.d/vault.hcl
|
||||
ui = true
|
||||
disable_mlock = true
|
||||
|
||||
storage "raft" {
|
||||
path = "/opt/vault/data"
|
||||
node_id = "$instance_id"
|
||||
retry_join {
|
||||
auto_join = "provider=aws region=${region} tag_key=${name}-vault tag_value=server"
|
||||
auto_join_scheme = "https"
|
||||
leader_tls_servername = "${leader_tls_servername}"
|
||||
leader_ca_cert_file = "/opt/vault/tls/vault-ca.pem"
|
||||
leader_client_cert_file = "/opt/vault/tls/vault-cert.pem"
|
||||
leader_client_key_file = "/opt/vault/tls/vault-key.pem"
|
||||
}
|
||||
}
|
||||
|
||||
cluster_addr = "https://$local_ipv4:8201"
|
||||
api_addr = "https://$local_ipv4:8200"
|
||||
|
||||
listener "tcp" {
|
||||
address = "0.0.0.0:8200"
|
||||
tls_disable = false
|
||||
tls_cert_file = "/opt/vault/tls/vault-cert.pem"
|
||||
tls_key_file = "/opt/vault/tls/vault-key.pem"
|
||||
tls_client_ca_file = "/opt/vault/tls/vault-ca.pem"
|
||||
}
|
||||
|
||||
seal "awskms" {
|
||||
region = "${region}"
|
||||
kms_key_id = "${kms_key_arn}"
|
||||
}
|
||||
|
||||
EOF
|
||||
|
||||
# vault.hcl should be readable by the vault group only
|
||||
chown root:root /etc/vault.d
|
||||
chown root:vault /etc/vault.d/vault.hcl
|
||||
chmod 640 /etc/vault.d/vault.hcl
|
||||
|
||||
systemctl enable vault
|
||||
systemctl start vault
|
||||
|
||||
echo "Setup Vault profile"
|
||||
cat <<PROFILE | sudo tee /etc/profile.d/vault.sh
|
||||
export VAULT_ADDR="https://127.0.0.1:8200"
|
||||
export VAULT_CACERT="/opt/vault/tls/vault-ca.pem"
|
||||
PROFILE
|
|
@ -0,0 +1,43 @@
|
|||
/**
|
||||
* 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" {
|
||||
type = string
|
||||
description = "AWS region where Vault is being deployed"
|
||||
}
|
||||
|
||||
variable "kms_key_arn" {
|
||||
type = string
|
||||
description = "KMS Key ARN used for Vault auto-unseal"
|
||||
}
|
||||
|
||||
variable "leader_tls_servername" {
|
||||
type = string
|
||||
description = "One of the shared DNS SAN used to create the certs use for mTLS"
|
||||
default = "vault.great-hyperlobic-omnicognate-neutron-wrangler.space"
|
||||
}
|
||||
|
||||
variable "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
}
|
||||
|
||||
variable "secrets_manager_arn" {
|
||||
type = string
|
||||
description = "Secrets manager ARN where TLS cert info is stored"
|
||||
}
|
||||
|
||||
variable "user_supplied_userdata_path" {
|
||||
type = string
|
||||
description = "File path to custom userdata script being supplied by the user"
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "vault_version" {
|
||||
type = string
|
||||
description = "Vault version"
|
||||
}
|
|
@ -0,0 +1,30 @@
|
|||
# AWS VM Module
|
||||
|
||||
## Required variables
|
||||
|
||||
* `aws_iam_instance_profile` - IAM instance profile name to use for Vault instances
|
||||
* `lb_type` - The type of load balancer being used to front Vault instances
|
||||
* `resource_name_prefix` - Resource name prefix used for tagging and naming AWS resources
|
||||
* `userdata_script` - Userdata script for EC2 instance. Must be base64-encoded.
|
||||
* `vault_lb_sg_id` - Security group ID of Vault load balancer (will not be read if you are using a network load balancer)
|
||||
* `vault_subnets` - Private subnets where Vault will be deployed
|
||||
* `vault_target_group_arn` - Target group ARN to register Vault nodes with
|
||||
* `vpc_id` - VPC ID where Vault will be deployed
|
||||
|
||||
## Example usage
|
||||
|
||||
```hcl
|
||||
module "vm" {
|
||||
source = "./modules/vm"
|
||||
|
||||
aws_iam_instance_profile = var.aws_iam_instance_profile
|
||||
instance_type = var.instance_type
|
||||
lb_type = var.lb_type
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
userdata_script = var.userdata_script
|
||||
vault_lb_sg_id = var.vault_lb_sg_id
|
||||
vault_subnets = var.vault_subnet_ids
|
||||
vault_target_group_arn = var.vault_target_group_arn
|
||||
vpc_id = var.vpc_id
|
||||
}
|
||||
```
|
|
@ -0,0 +1,3 @@
|
|||
data "aws_ssm_parameter" "latest_ami" {
|
||||
name = "/aws/service/debian/release/12/latest/amd64"
|
||||
}
|
|
@ -0,0 +1,205 @@
|
|||
/**
|
||||
* 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/.
|
||||
*
|
||||
*/
|
||||
|
||||
data "aws_ami" "ubuntu" {
|
||||
count = var.user_supplied_ami_id != null ? 0 : 1
|
||||
most_recent = true
|
||||
|
||||
filter {
|
||||
name = "name"
|
||||
values = ["ubuntu/images/hvm-ssd/ubuntu-focal-20.04-amd64-server-*"]
|
||||
}
|
||||
|
||||
filter {
|
||||
name = "virtualization-type"
|
||||
values = ["hvm"]
|
||||
}
|
||||
|
||||
owners = ["099720109477"] # Canonical
|
||||
}
|
||||
|
||||
resource "aws_security_group" "vault" {
|
||||
name = "${var.resource_name_prefix}-vault"
|
||||
vpc_id = var.vpc_id
|
||||
|
||||
tags = merge(
|
||||
{ Name = "${var.resource_name_prefix}-vault-sg" },
|
||||
var.common_tags,
|
||||
)
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_internal_api" {
|
||||
description = "Allow Vault nodes to reach other on port 8200 for API"
|
||||
security_group_id = aws_security_group.vault.id
|
||||
type = "ingress"
|
||||
from_port = 8200
|
||||
to_port = 8200
|
||||
protocol = "tcp"
|
||||
self = true
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_internal_raft" {
|
||||
description = "Allow Vault nodes to communicate on port 8201 for replication traffic, request forwarding, and Raft gossip"
|
||||
security_group_id = aws_security_group.vault.id
|
||||
type = "ingress"
|
||||
from_port = 8201
|
||||
to_port = 8201
|
||||
protocol = "tcp"
|
||||
self = true
|
||||
}
|
||||
|
||||
# The following data source gets used if the user has
|
||||
# specified a network load balancer.
|
||||
# This will lock down the EC2 instance security group to
|
||||
# just the subnets that the load balancer spans
|
||||
# (which are the private subnets the Vault instances use)
|
||||
|
||||
data "aws_subnet" "subnet" {
|
||||
count = length(var.vault_subnets)
|
||||
id = var.vault_subnets[count.index]
|
||||
}
|
||||
|
||||
locals {
|
||||
subnet_cidr_blocks = [for s in data.aws_subnet.subnet : s.cidr_block]
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_network_lb_inbound" {
|
||||
count = var.lb_type == "network" ? 1 : 0
|
||||
description = "Allow load balancer to reach Vault nodes on port 8200"
|
||||
security_group_id = aws_security_group.vault.id
|
||||
type = "ingress"
|
||||
from_port = 8200
|
||||
to_port = 8200
|
||||
protocol = "tcp"
|
||||
cidr_blocks = local.subnet_cidr_blocks
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_application_lb_inbound" {
|
||||
count = var.lb_type == "application" ? 1 : 0
|
||||
description = "Allow load balancer to reach Vault nodes on port 8200"
|
||||
security_group_id = aws_security_group.vault.id
|
||||
type = "ingress"
|
||||
from_port = 8200
|
||||
to_port = 8200
|
||||
protocol = "tcp"
|
||||
source_security_group_id = var.vault_lb_sg_id
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_network_lb_ingress" {
|
||||
count = var.lb_type == "network" && var.allowed_inbound_cidrs != null ? 1 : 0
|
||||
description = "Allow specified CIDRs access to load balancer and nodes on port 8200"
|
||||
security_group_id = aws_security_group.vault.id
|
||||
type = "ingress"
|
||||
from_port = 8200
|
||||
to_port = 8200
|
||||
protocol = "tcp"
|
||||
cidr_blocks = var.allowed_inbound_cidrs
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_ssh_inbound" {
|
||||
count = var.allowed_inbound_cidrs_ssh != null ? 1 : 0
|
||||
description = "Allow specified CIDRs SSH access to Vault nodes"
|
||||
security_group_id = aws_security_group.vault.id
|
||||
type = "ingress"
|
||||
from_port = 22
|
||||
to_port = 22
|
||||
protocol = "tcp"
|
||||
cidr_blocks = var.allowed_inbound_cidrs_ssh
|
||||
}
|
||||
|
||||
resource "aws_security_group_rule" "vault_outbound" {
|
||||
description = "Allow Vault nodes to send outbound traffic"
|
||||
security_group_id = aws_security_group.vault.id
|
||||
type = "egress"
|
||||
from_port = 0
|
||||
to_port = 0
|
||||
protocol = "-1"
|
||||
cidr_blocks = ["0.0.0.0/0"]
|
||||
}
|
||||
|
||||
resource "aws_launch_template" "vault" {
|
||||
name = "${var.resource_name_prefix}-vault"
|
||||
image_id = var.user_supplied_ami_id != null ? var.user_supplied_ami_id : data.aws_ssm_parameter.latest_ami.value
|
||||
instance_type = var.instance_type
|
||||
key_name = var.key_name != null ? var.key_name : null
|
||||
user_data = var.userdata_script
|
||||
vpc_security_group_ids = [
|
||||
aws_security_group.vault.id,
|
||||
]
|
||||
|
||||
block_device_mappings {
|
||||
device_name = "/dev/sda1"
|
||||
|
||||
ebs {
|
||||
volume_type = "gp3"
|
||||
volume_size = 100
|
||||
throughput = 150
|
||||
iops = 3000
|
||||
delete_on_termination = true
|
||||
}
|
||||
}
|
||||
|
||||
iam_instance_profile {
|
||||
name = var.aws_iam_instance_profile
|
||||
}
|
||||
|
||||
metadata_options {
|
||||
http_endpoint = "enabled"
|
||||
http_tokens = "required"
|
||||
}
|
||||
}
|
||||
|
||||
resource "aws_autoscaling_group" "vault" {
|
||||
name = "${var.resource_name_prefix}-vault"
|
||||
min_size = var.node_count
|
||||
max_size = var.node_count + 2
|
||||
desired_capacity = var.node_count
|
||||
vpc_zone_identifier = var.vault_subnets
|
||||
target_group_arns = var.vault_target_group_arns
|
||||
|
||||
|
||||
launch_template {
|
||||
id = aws_launch_template.vault.id
|
||||
version = "$Latest"
|
||||
}
|
||||
|
||||
enabled_metrics = [
|
||||
"GroupDesiredCapacity",
|
||||
"GroupInServiceCapacity",
|
||||
"GroupPendingCapacity",
|
||||
"GroupMinSize",
|
||||
"GroupMaxSize",
|
||||
"GroupInServiceInstances",
|
||||
"GroupPendingInstances",
|
||||
"GroupStandbyInstances",
|
||||
"GroupStandbyCapacity",
|
||||
"GroupTerminatingCapacity",
|
||||
"GroupTerminatingInstances",
|
||||
"GroupTotalCapacity",
|
||||
"GroupTotalInstances"
|
||||
]
|
||||
|
||||
tag {
|
||||
key = "Name"
|
||||
value = "${var.resource_name_prefix}-vault-server"
|
||||
propagate_at_launch = true
|
||||
}
|
||||
dynamic "tag" {
|
||||
for_each = var.common_tags
|
||||
content {
|
||||
key = tag.key
|
||||
value = tag.value
|
||||
propagate_at_launch = true
|
||||
}
|
||||
}
|
||||
tag {
|
||||
key = "${var.resource_name_prefix}-vault"
|
||||
value = "server"
|
||||
propagate_at_launch = true
|
||||
}
|
||||
|
||||
}
|
|
@ -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 "asg_name" {
|
||||
description = "Name of autoscaling group"
|
||||
value = aws_autoscaling_group.vault.name
|
||||
}
|
||||
|
||||
output "launch_template_id" {
|
||||
description = "ID of launch template for Vault autoscaling group"
|
||||
value = aws_launch_template.vault.id
|
||||
}
|
||||
|
||||
output "vault_sg_id" {
|
||||
description = "Security group ID of Vault cluster"
|
||||
value = aws_security_group.vault.id
|
||||
}
|
|
@ -0,0 +1,86 @@
|
|||
/**
|
||||
* 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 "allowed_inbound_cidrs" {
|
||||
type = list(string)
|
||||
description = "List of CIDR blocks to permit inbound traffic from to load balancer"
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "allowed_inbound_cidrs_ssh" {
|
||||
type = list(string)
|
||||
description = "List of CIDR blocks to give SSH access to Vault nodes"
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "aws_iam_instance_profile" {
|
||||
type = string
|
||||
description = "IAM instance profile name to use for Vault instances"
|
||||
}
|
||||
|
||||
variable "common_tags" {
|
||||
type = map(string)
|
||||
description = "(Optional) Map of common tags for all taggable AWS resources."
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "instance_type" {
|
||||
type = string
|
||||
description = "EC2 instance type"
|
||||
}
|
||||
|
||||
variable "key_name" {
|
||||
type = string
|
||||
description = "key pair to use for SSH access to instance"
|
||||
}
|
||||
|
||||
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
|
||||
}
|
||||
|
||||
variable "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
}
|
||||
|
||||
variable "userdata_script" {
|
||||
type = string
|
||||
description = "Userdata script for EC2 instance"
|
||||
}
|
||||
|
||||
variable "user_supplied_ami_id" {
|
||||
type = string
|
||||
description = "AMI ID to use with Vault instances"
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "vault_lb_sg_id" {
|
||||
type = string
|
||||
description = "Security group ID of Vault load balancer"
|
||||
}
|
||||
|
||||
variable "vault_subnets" {
|
||||
type = list(string)
|
||||
description = "Private subnets where Vault will be deployed"
|
||||
}
|
||||
|
||||
variable "vault_target_group_arns" {
|
||||
type = list(string)
|
||||
description = "Target group ARN(s) to register Vault nodes with"
|
||||
}
|
||||
|
||||
variable "vpc_id" {
|
||||
type = string
|
||||
description = "VPC ID where Vault will be deployed"
|
||||
}
|
|
@ -0,0 +1,71 @@
|
|||
/**
|
||||
* 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 "asg_name" {
|
||||
value = module.vm.asg_name
|
||||
}
|
||||
|
||||
output "kms_key_arn" {
|
||||
value = module.kms.kms_key_arn
|
||||
}
|
||||
|
||||
output "launch_template_id" {
|
||||
value = module.vm.launch_template_id
|
||||
}
|
||||
|
||||
output "vault_lb_dns_name" {
|
||||
description = "DNS name of Vault load balancer"
|
||||
value = module.loadbalancer.vault_lb_dns_name
|
||||
}
|
||||
|
||||
output "vault_lb_zone_id" {
|
||||
description = "Zone ID of Vault load balancer"
|
||||
value = module.loadbalancer.vault_lb_zone_id
|
||||
}
|
||||
|
||||
output "vault_lb_arn" {
|
||||
description = "ARN of Vault load balancer"
|
||||
value = module.loadbalancer.vault_lb_arn
|
||||
}
|
||||
|
||||
output "vault_target_group_arn" {
|
||||
description = "Target group ARN to register Vault nodes with"
|
||||
value = module.loadbalancer.vault_target_group_arn
|
||||
}
|
||||
|
||||
output "vault_sg_id" {
|
||||
description = "Security group ID of Vault cluster"
|
||||
value = module.vm.vault_sg_id
|
||||
}
|
||||
|
||||
# supplied by ./modules/vps-secrets
|
||||
|
||||
# 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
|
||||
# }
|
||||
|
|
@ -0,0 +1,194 @@
|
|||
/**
|
||||
* 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 "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Prefix for resource names in VPC infrastructure"
|
||||
default = "vault"
|
||||
}
|
||||
|
||||
|
||||
variable "key_name" {
|
||||
type = string
|
||||
default = null
|
||||
description = "(Optional) key pair to use for SSH access to instance"
|
||||
}
|
||||
|
||||
variable "lb_deregistration_delay" {
|
||||
type = string
|
||||
description = "Amount time, in seconds, for Vault LB target group to wait before changing the state of a deregistering target from draining to unused."
|
||||
default = 300
|
||||
}
|
||||
|
||||
variable "permissions_boundary" {
|
||||
description = "(Optional) IAM Managed Policy to serve as permissions boundary for created IAM Roles"
|
||||
type = string
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "vault_version" {
|
||||
type = string
|
||||
default = "1.15.5"
|
||||
description = "Vault version"
|
||||
}
|
||||
|
||||
variable "vpc_id" {
|
||||
type = string
|
||||
description = "VPC ID where Vault will be deployed"
|
||||
}
|
||||
|
||||
variable "aws_region" {
|
||||
description = "AWS region to deploy resources into"
|
||||
type = string
|
||||
default = "us-east-1"
|
||||
}
|
||||
|
||||
# === General ===
|
||||
|
||||
variable "common_tags" {
|
||||
type = map(string)
|
||||
description = "(Optional) Map of common tags for all taggable AWS resources."
|
||||
default = {
|
||||
"project" = "vault"
|
||||
}
|
||||
}
|
||||
|
||||
variable "tags" {
|
||||
type = map(string)
|
||||
description = "Tags for VPC resources"
|
||||
default = {
|
||||
"Terraform" = "true"
|
||||
"Environment" = "dev"
|
||||
"Project" = "vault"
|
||||
}
|
||||
}
|
||||
|
||||
# === config ===
|
||||
|
||||
variable "instance_type" {
|
||||
type = string
|
||||
description = "The instance type to use for Vault nodes"
|
||||
default = "t3.micro"
|
||||
}
|
||||
variable "additional_lb_target_groups" {
|
||||
type = list(string)
|
||||
description = "(Optional) List of load balancer target groups to associate with the Vault cluster. These target groups are _in addition_ to the LB target group this module provisions by default."
|
||||
default = []
|
||||
}
|
||||
|
||||
variable "lb_type" {
|
||||
description = "The type of load balancer to provision; network or application."
|
||||
type = string
|
||||
default = "application"
|
||||
|
||||
validation {
|
||||
condition = contains(["application", "network"], var.lb_type)
|
||||
error_message = "The variable lb_type must be one of: application, network."
|
||||
}
|
||||
}
|
||||
|
||||
variable "node_count" {
|
||||
type = number
|
||||
description = "**Required** Number of Vault nodes to deploy in ASG"
|
||||
default = 2
|
||||
}
|
||||
|
||||
# === user supplied variables ===
|
||||
|
||||
variable "user_supplied_ami_id" {
|
||||
type = string
|
||||
description = "**Required** 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 = "**Required** 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 = "**Required** 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 = "**Required** File path to custom userdata script being supplied by the user"
|
||||
default = null
|
||||
}
|
||||
|
||||
# === VPC ===
|
||||
|
||||
variable "azs" {
|
||||
description = "availability zones to use in AWS region"
|
||||
type = list(string)
|
||||
default = [
|
||||
"eu-north-1a",
|
||||
"eu-north-1b",
|
||||
]
|
||||
}
|
||||
|
||||
variable "allowed_inbound_cidrs_lb" {
|
||||
type = list(string)
|
||||
description = "**Required** 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 = "**Required** CIDR blocks to allow inbound SSH traffic to the Vault instances"
|
||||
default = ["0.0.0.0/0"]
|
||||
}
|
||||
|
||||
# === Certs ===
|
||||
variable "ssl_policy" {
|
||||
type = string
|
||||
description = "**Required** The SSL policy to use for the load balancer"
|
||||
default = "ELBSecurityPolicy-TLS-1-2-2017-01"
|
||||
}
|
||||
|
||||
variable "lb_health_check_path" {
|
||||
type = string
|
||||
description = "The endpoint to check for Vault's health status."
|
||||
default = "/v1/sys/health?activecode=200&standbycode=200&sealedcode=200&uninitcode=200"
|
||||
}
|
||||
|
||||
variable "kms_key_deletion_window" {
|
||||
type = number
|
||||
default = 7
|
||||
description = "**Required**Duration in days after which the key is deleted after destruction of the resource (must be between 7 and 30 days)."
|
||||
}
|
||||
|
||||
# === Supplied by ./modules/vpc-secrets ===
|
||||
|
||||
variable "secrets_manager_arn" {
|
||||
type = string
|
||||
description = "**Supplied by module/vpc-secrets** **Required** Secrets manager ARN where TLS cert info is stored"
|
||||
}
|
||||
|
||||
variable "leader_tls_servername" {
|
||||
type = string
|
||||
description = "**Supplied by module/vpc-secrets** **Required** One of the shared DNS SAN used to create the certs use for mTLS"
|
||||
default = "vault.great-hyperlobic-omnicognate-neutron-wrangler.space"
|
||||
}
|
||||
|
||||
variable "lb_certificate_arn" {
|
||||
type = string
|
||||
description = "**Supplied by module/vpc-secrets** **Required** ARN of TLS certificate imported into ACM for use with LB listener"
|
||||
}
|
||||
|
||||
# variable "vpc_id" {
|
||||
# type = string
|
||||
# description = "**Supplied by module/vpc-secrets** **Required** VPC ID where Vault will be deployed"
|
||||
# }
|
||||
|
||||
variable "private_subnet_ids" {
|
||||
type = list(string)
|
||||
description = "**Supplied by module/vpc-secrets** **Required** Subnet IDs to deploy Vault into"
|
||||
}
|
|
@ -0,0 +1,14 @@
|
|||
/**
|
||||
* 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.7.0"
|
||||
|
||||
required_providers {
|
||||
aws = ">= 4.0.0"
|
||||
}
|
||||
}
|
|
@ -0,0 +1,3 @@
|
|||
data "aws_ssm_parameter" "latest_ami" {
|
||||
name = "/aws/service/debian/release/12/latest/amd64"
|
||||
}
|
|
@ -0,0 +1,51 @@
|
|||
/**
|
||||
* 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 = "./modules/aws-vpc/"
|
||||
|
||||
azs = var.azs
|
||||
common_tags = var.tags
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
}
|
||||
|
||||
module "secrets" {
|
||||
source = "./modules/vpc-secrets/"
|
||||
shared_san = var.shared_san
|
||||
resource_name_prefix = var.resource_name_prefix
|
||||
}
|
||||
|
||||
module "bastion" {
|
||||
source = "Guimove/bastion/aws"
|
||||
bastion_ami = var.use_latest_ami ? data.aws_ssm_parameter.latest_ami.value : var.user_supplied_ami_id
|
||||
bucket_name = var.bastion_bucket_name
|
||||
region = var.aws_region
|
||||
vpc_id = module.vpc.vpc_id
|
||||
is_lb_private = "false"
|
||||
bastion_host_key_pair = "Vault"
|
||||
create_dns_record = "true"
|
||||
hosted_zone_id = var.hosted_zone_id
|
||||
bastion_record_name = var.bastion_record_name
|
||||
bastion_iam_policy_name = "VaultBastionHostPolicy"
|
||||
elb_subnets = [
|
||||
"subnet-id1a",
|
||||
"subnet-id1b"
|
||||
]
|
||||
auto_scaling_group_subnets = [
|
||||
"subnet-id1a",
|
||||
"subnet-id1b"
|
||||
]
|
||||
tags = merge(
|
||||
{ "Name" = "${var.resource_name_prefix}-bastion"},
|
||||
var.common_tags
|
||||
)
|
||||
}
|
||||
|
|
@ -7,7 +7,7 @@
|
|||
|
||||
module "vpc" {
|
||||
source = "terraform-aws-modules/vpc/aws"
|
||||
version = "3.0.0"
|
||||
version = "~>5.5.0"
|
||||
name = "${var.resource_name_prefix}-vault"
|
||||
cidr = var.vpc_cidr
|
||||
azs = var.azs
|
|
@ -8,6 +8,7 @@
|
|||
variable "azs" {
|
||||
description = "availability zones to use in AWS region"
|
||||
type = list(string)
|
||||
default = ["eu-north-1a", "eu-north-1b"]
|
||||
}
|
||||
|
||||
variable "common_tags" {
|
||||
|
@ -26,7 +27,7 @@ variable "private_subnet_cidrs" {
|
|||
default = [
|
||||
"10.0.0.0/19",
|
||||
"10.0.32.0/19",
|
||||
"10.0.64.0/19",
|
||||
# "10.0.64.0/19",
|
||||
]
|
||||
}
|
||||
|
||||
|
@ -36,7 +37,7 @@ variable "public_subnet_cidrs" {
|
|||
default = [
|
||||
"10.0.128.0/20",
|
||||
"10.0.144.0/20",
|
||||
"10.0.160.0/20",
|
||||
# "10.0.160.0/20",
|
||||
]
|
||||
}
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
locals {
|
||||
name_prefix = var.bastion_launch_template_name
|
||||
security_group = join("", flatten([aws_security_group.bastion_host_security_group[*].id, var.bastion_security_group_id]))
|
||||
|
||||
// the compact() function checks for null values and gets rid of them
|
||||
// the length is a check to ensure we dont have an empty array, as an empty array would throw an error for the cidr_block argument
|
||||
ipv4_cidr_block = length(compact(data.aws_subnet.subnets[*].cidr_block)) == 0 ? null : concat(data.aws_subnet.subnets[*].cidr_block, var.cidrs)
|
||||
ipv6_cidr_block = length(compact(data.aws_subnet.subnets[*].ipv6_cidr_block)) == 0 ? null : concat(data.aws_subnet.subnets[*].ipv6_cidr_block, var.ipv6_cidrs)
|
||||
}
|
|
@ -0,0 +1,89 @@
|
|||
# Load Balancer
|
||||
#
|
||||
# HTTPS is terminated at the load balancer. The load balancer will then communicate
|
||||
# with the targets over HTTP. The Targets (vault instances) are in a private
|
||||
# subnet, cut off from any external access. This means that they're still perfectly
|
||||
# secure AND we don't incur the overhead of extra TLS handshakes and encryption.
|
||||
|
||||
## Application Load Balancer
|
||||
resource "aws_lb" "alb" {
|
||||
// Can't give it a full name_prefix due to 32 character limit on LBs
|
||||
// and the fact that Terraform adds a 26 character random bit to the end.
|
||||
// https://github.com/terraform-providers/terraform-provider-aws/issues/1666
|
||||
name_prefix = "vault-"
|
||||
internal = var.private_mode
|
||||
load_balancer_type = "application"
|
||||
security_groups = [aws_security_group.load_balancer.id]
|
||||
subnets = aws_subnet.public.*.id
|
||||
idle_timeout = 60
|
||||
ip_address_type = var.private_mode ? "ipv4" : "dualstack"
|
||||
|
||||
tags = merge(
|
||||
{ "Name" = "${var.main_project_tag}-alb"},
|
||||
{ "Project" = var.main_project_tag }
|
||||
)
|
||||
}
|
||||
|
||||
## Target Group
|
||||
resource "aws_lb_target_group" "alb_targets" {
|
||||
name_prefix = "vault-"
|
||||
port = 8200
|
||||
protocol = "HTTPS"
|
||||
vpc_id = aws_vpc.vault.id
|
||||
deregistration_delay = 30
|
||||
target_type = "instance"
|
||||
|
||||
health_check {
|
||||
enabled = true
|
||||
interval = 10
|
||||
path = "/v1/sys/health" // the Vault API health port
|
||||
protocol = "HTTPS"
|
||||
timeout = 5
|
||||
healthy_threshold = 3
|
||||
unhealthy_threshold = 3
|
||||
matcher = "200"
|
||||
}
|
||||
|
||||
tags = merge(
|
||||
{ "Name" = "${var.main_project_tag}-tg"},
|
||||
{ "Project" = var.main_project_tag }
|
||||
)
|
||||
}
|
||||
|
||||
## Load Balancer Listeners
|
||||
|
||||
### Redirect to HTTPS
|
||||
resource "aws_lb_listener" "alb_http_redirect" {
|
||||
load_balancer_arn = aws_lb.alb.arn
|
||||
port = 80
|
||||
protocol = "HTTP"
|
||||
|
||||
default_action {
|
||||
type = "redirect"
|
||||
|
||||
// For information on the below reserved keywords
|
||||
// https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-listeners.html#rule-action-types
|
||||
redirect {
|
||||
host = "#{host}"
|
||||
path = "/#{path}"
|
||||
port = 443
|
||||
protocol = "HTTPS"
|
||||
query = "#{query}"
|
||||
status_code = "HTTP_301"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
### HTTPS
|
||||
resource "aws_lb_listener" "alb_https" {
|
||||
load_balancer_arn = aws_lb.alb.arn
|
||||
port = 443
|
||||
protocol = "HTTPS"
|
||||
ssl_policy = "ELBSecurityPolicy-FS-2018-06" // Enable Forward Secrecy
|
||||
certificate_arn = data.aws_acm_certificate.vault_alb_cert.arn
|
||||
|
||||
default_action {
|
||||
type = "forward"
|
||||
target_group_arn = aws_lb_target_group.alb_targets.arn
|
||||
}
|
||||
}
|
|
@ -0,0 +1,23 @@
|
|||
# === General ===
|
||||
|
||||
variable "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
default = "prod-vault"
|
||||
}
|
||||
|
||||
variable "common_tags" {
|
||||
type = map(string)
|
||||
description = "(Optional) Map of common tags for all taggable AWS resources."
|
||||
default = {
|
||||
"project" = "vault"
|
||||
}
|
||||
}
|
||||
|
||||
# === Config ===
|
||||
|
||||
variable "key_name" {
|
||||
description = "(Optional) key pair to use for SSH access to instance"
|
||||
type = string
|
||||
default = "Vault"
|
||||
}
|
|
@ -48,7 +48,7 @@ resource "tls_cert_request" "server" {
|
|||
private_key_pem = tls_private_key.server.private_key_pem
|
||||
|
||||
subject {
|
||||
common_name = "vault.server.com"
|
||||
common_name = var.shared_san
|
||||
}
|
||||
|
||||
dns_names = [
|
||||
|
@ -76,9 +76,9 @@ resource "tls_locally_signed_cert" "server" {
|
|||
"server_auth",
|
||||
]
|
||||
|
||||
# provisioner "local-exec" {
|
||||
# command = "echo '${tls_locally_signed_cert.server.cert_pem}' > ./vault-crt.pem"
|
||||
# }
|
||||
provisioner "local-exec" {
|
||||
command = "echo '${tls_locally_signed_cert.server.cert_pem}' > ./vault-crt.pem"
|
||||
}
|
||||
}
|
||||
|
||||
locals {
|
|
@ -26,7 +26,6 @@ variable "resource_name_prefix" {
|
|||
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" {
|
|
@ -30,3 +30,4 @@ output "vpc_id" {
|
|||
value = module.vpc.vpc_id
|
||||
}
|
||||
|
||||
|
|
@ -0,0 +1,96 @@
|
|||
/**
|
||||
* 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)
|
||||
}
|
||||
|
||||
variable "shared_san" {
|
||||
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."
|
||||
type = string
|
||||
default = "vault.great-hyperlobic-omnicognate-neutron-wrangler.space"
|
||||
}
|
||||
|
||||
variable "tags" {
|
||||
description = "Tags for VPC resources"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "resource_name_prefix" {
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
type = string
|
||||
default = "prod"
|
||||
}
|
||||
|
||||
# === Bastion ===
|
||||
|
||||
variable "bastion_bucket_name" {
|
||||
description = "Bucket name where the bastion will store the logs"
|
||||
type = string
|
||||
default = "omnicognate-vault-bastion-access-logs"
|
||||
}
|
||||
|
||||
variable "create_dns_record" {
|
||||
description = "True or false?"
|
||||
type = bool
|
||||
default = true
|
||||
}
|
||||
|
||||
variable "hosted_zone_id" {
|
||||
description = "Name of the hosted zone where we'll register the bastion DNS name"
|
||||
type = string
|
||||
default = "vault.great-hyperlobic-omnicognate-neutron-wrangler.space"
|
||||
}
|
||||
|
||||
|
||||
variable "bastion_record_name" {
|
||||
description = ""
|
||||
type = string
|
||||
default = "vault.vault.great-hyperlobic-omnicognate-neutron-wrangler.space"
|
||||
}
|
||||
|
||||
|
||||
|
||||
variable "common_tags" {
|
||||
type = map(string)
|
||||
description = "(Optional) Map of common tags for all taggable AWS resources."
|
||||
default = {
|
||||
"project" = "vault"
|
||||
}
|
||||
}
|
||||
|
||||
variable "use_latest_ami" {
|
||||
description = "Use the latest AMI for bastion?"
|
||||
type = bool
|
||||
default = true
|
||||
}
|
||||
|
||||
variable "user_supplied_ami_id" {
|
||||
description = "User-provided AMI ID to use with bastion."
|
||||
type = string
|
||||
default = "ami-0506d6d51f1916a96"
|
||||
}
|
||||
|
||||
variable "bastion_instance_type" {
|
||||
description = "The instance type to use for the bastion"
|
||||
type = string
|
||||
default = "t3.micro"
|
||||
}
|
||||
|
||||
variable "key_name" {
|
||||
description = "(Optional) key pair to use for SSH access to instance"
|
||||
type = string
|
||||
default = "Vault"
|
||||
}
|
|
@ -1,25 +0,0 @@
|
|||
/**
|
||||
* 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
|
||||
}
|
||||
|
|
@ -1,32 +0,0 @@
|
|||
/**
|
||||
* 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"
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
# output "lb_certificate_arn" {
|
||||
# description = "ARN of ACM cert to use with Vault LB listener"
|
||||
# value = module.networking.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.networking.leader_tls_servername
|
||||
# }
|
||||
|
||||
# output "private_subnet_ids" {
|
||||
# description = "Private subnet IDs"
|
||||
# value = module.networking.private_subnet_ids
|
||||
# }
|
||||
|
||||
# output "secrets_manager_arn" {
|
||||
# description = "ARN of secrets_manager secret"
|
||||
# value = module.networking.secrets_manager_arn
|
||||
# }
|
||||
|
||||
# output "vpc_id" {
|
||||
# description = "The ID of the VPC"
|
||||
# value = module.networking.vpc_id
|
||||
# }
|
||||
|
||||
output "role_arn" {
|
||||
description = "The ARN of the role"
|
||||
value = var.role_arn
|
||||
|
||||
}
|
||||
|
||||
output "key_name" {
|
||||
description = "The name of the key"
|
||||
value = var.key_name
|
||||
}
|
15
providers.tf
15
providers.tf
|
@ -1,13 +1,22 @@
|
|||
terraform {
|
||||
required_version = ">= 1.0"
|
||||
backend "s3" {
|
||||
# PROVIDE THIS KEY ... FILE ISOLATION
|
||||
key = "vault-prod/terraform.tfstate"
|
||||
# PROVIDE THIS KEY ... FILE ISOLATION
|
||||
}
|
||||
required_version = ">= 1.7.0"
|
||||
required_providers {
|
||||
aws = {
|
||||
source = "hashicorp/aws"
|
||||
version = ">= 3.15.0"
|
||||
version = ">= 4.0.0"
|
||||
}
|
||||
}
|
||||
}
|
||||
provider "aws" {
|
||||
region = var.aws_region
|
||||
profile = var.aws_profile
|
||||
# using aws-vault to assume a role
|
||||
assume_role {
|
||||
duration = "1h"
|
||||
role_arn = var.role_arn
|
||||
}
|
||||
}
|
||||
|
|
69
variables.tf
69
variables.tf
|
@ -3,7 +3,7 @@
|
|||
variable "resource_name_prefix" {
|
||||
type = string
|
||||
description = "Resource name prefix used for tagging and naming AWS resources"
|
||||
default = "vault"
|
||||
default = "prod"
|
||||
}
|
||||
|
||||
variable "vault_version" {
|
||||
|
@ -18,16 +18,15 @@ variable "aws_region" {
|
|||
default = "eu-north-1"
|
||||
}
|
||||
|
||||
variable "aws_profile" {
|
||||
variable "role_arn" {
|
||||
type = string
|
||||
description = "The AWS Profile to use for this project."
|
||||
default = "tf_dev"
|
||||
description = "The assumed role to use for this project."
|
||||
}
|
||||
|
||||
variable "key_name" {
|
||||
description = "(Optional) key pair to use for SSH access to instance"
|
||||
type = string
|
||||
default = "Vault"
|
||||
description = "(Optional) key pair to use for SSH access to instance"
|
||||
}
|
||||
|
||||
variable "common_tags" {
|
||||
|
@ -38,6 +37,7 @@ variable "common_tags" {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
# === config ===
|
||||
|
||||
variable "instance_type" {
|
||||
|
@ -45,10 +45,10 @@ variable "instance_type" {
|
|||
description = "The instance type to use for Vault nodes"
|
||||
default = "t3.micro"
|
||||
}
|
||||
variable "additional_lb_target_groups" {
|
||||
type = list(string)
|
||||
description = "(Optional) List of load balancer target groups to associate with the Vault cluster. These target groups are _in addition_ to the LB target group this module provisions by default."
|
||||
default = []
|
||||
|
||||
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."
|
||||
}
|
||||
|
||||
variable "lb_type" {
|
||||
|
@ -72,30 +72,39 @@ variable "node_count" {
|
|||
|
||||
variable "user_supplied_ami_id" {
|
||||
type = string
|
||||
description = "**Required** 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."
|
||||
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 = "ami-0506d6d51f1916a96"
|
||||
}
|
||||
|
||||
variable "user_supplied_iam_role_name" {
|
||||
type = string
|
||||
description = "**Required** 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_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 = "**Required** User-provided KMS key ARN. Providing this will disable the KMS submodule from generating a KMS key used for Vault auto-unseal"
|
||||
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 = "**Required** File path to custom userdata script being supplied by the user"
|
||||
default = "./temp/userdata.sh"
|
||||
}
|
||||
# variable "user_supplied_userdata_path" {
|
||||
# type = string
|
||||
# description = "**Optional** File path to custom userdata script being supplied by the user"
|
||||
# default = null
|
||||
# }
|
||||
|
||||
# === VPC ===
|
||||
|
||||
variable "azs" {
|
||||
description = "availability zones to use in AWS region"
|
||||
type = list(string)
|
||||
default = [
|
||||
"eu-north-1a",
|
||||
"eu-north-1b",
|
||||
]
|
||||
}
|
||||
|
||||
variable "allowed_inbound_cidrs_lb" {
|
||||
type = list(string)
|
||||
description = "**Required** CIDR blocks to allow inbound traffic to the load balancer"
|
||||
|
@ -127,29 +136,29 @@ variable "kms_key_deletion_window" {
|
|||
description = "**Required**Duration in days after which the key is deleted after destruction of the resource (must be between 7 and 30 days)."
|
||||
}
|
||||
|
||||
# === Supplied by ./modules/vpc-secrets ===
|
||||
# === Supplied by ./modules/networking ===
|
||||
|
||||
# variable "secrets_manager_arn" {
|
||||
# type = string
|
||||
# description = "**Supplied by module/vpc-secrets** **Required** Secrets manager ARN where TLS cert info is stored"
|
||||
# description = "**Supplied by module/networking** **Required** Secrets manager ARN where TLS cert info is stored"
|
||||
# }
|
||||
|
||||
# variable "leader_tls_servername" {
|
||||
# type = string
|
||||
# description = "**Supplied by module/vpc-secrets** **Required** One of the shared DNS SAN used to create the certs use for mTLS"
|
||||
# }
|
||||
variable "leader_tls_servername" {
|
||||
type = string
|
||||
description = "**Supplied by module/networking** **Required** One of the shared DNS SAN used to create the certs use for mTLS"
|
||||
}
|
||||
|
||||
# variable "lb_certificate_arn" {
|
||||
# type = string
|
||||
# description = "**Supplied by module/vpc-secrets** **Required** ARN of TLS certificate imported into ACM for use with LB listener"
|
||||
# description = "**Supplied by module/networking** **Required** ARN of TLS certificate imported into ACM for use with LB listener"
|
||||
# }
|
||||
|
||||
# variable "vpc_id" {
|
||||
# type = string
|
||||
# description = "**Supplied by module/vpc-secrets** **Required** VPC ID where Vault will be deployed"
|
||||
# description = "**Supplied by module/networking** **Required** VPC ID where Vault will be deployed"
|
||||
# }
|
||||
|
||||
# variable "private_subnet_ids" {
|
||||
# type = list(string)
|
||||
# description = "**Supplied by module/vpc-secrets** **Required** Subnet IDs to deploy Vault into"
|
||||
# description = "**Supplied by module/networking** **Required** Subnet IDs to deploy Vault into"
|
||||
# }
|
||||
|
|
Binary file not shown.
Loading…
Reference in New Issue